Home  >  Article  >  Database  >  Use Redis to complete the ranking system

Use Redis to complete the ranking system

齐天大圣
齐天大圣Original
2020-05-14 09:41:472031browse

There is a very special data type in redis - ordered set. The concept of a set we learned before is that all elements in the set are unique and unordered. But why does an ordered set appear here, and how does it achieve order?

The elements in the ordered set are still unique, but a socre (score) is set for each element, and ordering is achieved through this score. As shown in the figure below:

Use Redis to complete the ranking system

Ordered Set API

The following introduces several ordered sets API, you need to know the usage of these APIs to implement the ranking function.

zAdd

We want to set up an ordered list of player 2k ability values, using the player name element and the ability value as scores.

Curry's shooting ability is 100, James is 92, Harden is 96, Paul is 97

sadd can add 1 or more elements at a time

127.0.0.1:6379[1]> zadd 2kplayer:shoot 100 curry
(integer) 1
127.0.0.1:6379[1]> zadd 2kplayer:shoot 92 james 96 harden 97 paul
(integer) 3

zIncrBy

In the past month, Harden has been booming and scoring crazy high scores. So, 2k decided to increase his shooting ability by 2 points

127.0.0.1:6379[1]> zincrby 2kplayer:shoot 2 harden
"98"

zRange, zRevRange

Now we want to know who the top 3 players are.

127.0.0.1:6379[1]> zrange 2kplayer:shoot 0 2 withscores
1) "james"
2) "92"
3) "paul"
4) "97"
5) "harden"
6) "98"

Redis uses positive order by default, and the scores are sorted from small to large. So we need to use zRevRange

127.0.0.1:6379[1]> zrevrange 2kplayer:shoot 0 2 withscores
1) "curry"
2) "100"
3) "harden"
4) "98"
5) "paul"
6) "97"

zUnionStore

2k ability value has many aspects, shooting is only one of them, speed, layup etc. are all part of the ability value.

127.0.0.1:6379[1]> zadd 2kplayer:speed 99 james 90 paul 90 curry 93 harden 
(integer) 4

At this time, if you want to know the player's comprehensive ability value, you need to add up the scores for each item

127.0.0.1:6379[1]> zunionstore 2kplayer 2 2kplayer:shoot 2kplayer:speed
(integer) 4
127.0.0.1:6379[1]> zrange 2kplayer 0 -1 withscores
1) "paul"
2) "187"
3) "curry"
4) "190"
5) "harden"
6) "191"
7) "james"
8) "191"

Implement the ranking system

The scenario is as follows: a video on demand system with many people watching it every day. The system has a list function that displays the most viewed videos. It is divided into today's list, three-day list, weekly ranking and monthly list.

Idea: First, count the number of video views by day, and then count the today's list, three-day list, etc.

The pseudocode for counting the number of video views is as follows:

// 观看视频
function view ($videoId)
{
    $key = 'video:view:'.date('Y-m-d');  
      
    if (!$redis->exists($key)) {
        $redis->zIncrBy($key, 1, $videoId);
        $redis->expire($key, 86400 * 30);
    }
    
    $redis->zIncrBy($key, 1, $videoId);
}

Today’s Hottest

Today’s Hottest There is one thing to note , when a new day just starts, the data may be empty or very little. Therefore, we can combine today's and yesterday's data, but weight today's data higher.

The pseudo code for implementing today’s most popular functions is as follows:

function todayHot ()
{
    $tokeyKey = 'video:view:'.date('Y_m_d');
    $yesKey = 'video:view:'. date('Y_m_d', time() - 86400);
    $keyUnion = "view:rank:today";
    
    $redis->zUnionStore($keyUnion, [$tokeyKey, $yesKey], [10, 1]);
    // 取前100名
    return $redis->zRevRange($keyUnion, 0, 99);
}

Three-day list

function threeHot ()
{
    $keyUnion = 'view:rank:three';
    $unionKeys = [];
    
    for ($i=0; $i < 3; $i++) {
        $unionKeys[] = &#39;video:view:&#39;.date(&#39;Y_m_d&#39;, time() - 86400 *$i);
    }
    
    $redis->zUnionStore($keyUnion, $unionKeys);
    return $redis->zRevRange($keyUnion, 0, 99, true);
}

Weekly list, monthly list The list and other ideas are the same as the three-day list, so I won’t post the code.

The above is the detailed content of Use Redis to complete the ranking system. For more information, please follow other related articles on the PHP Chinese website!

Statement:
The content of this article is voluntarily contributed by netizens, and the copyright belongs to the original author. This site does not assume corresponding legal responsibility. If you find any content suspected of plagiarism or infringement, please contact admin@php.cn