redis zset转set 反序列化失败_Redis只往zset有序集合添加不存在的数据:关键字索引查询构建+源码分析...
Redis的有序集合Sorted Set(zset),可以很方便地用來構建關鍵字索引表,可以很方便地實現支持超大規模并發的關鍵字組合條件查詢。
比如有套博客系統,博客文章存放在 hash 類型 article:* 中,其中的每個關鍵字對應的文章存放在 keyword:* 中,則可以用關鍵字連接查詢 ZINTERSTORE 找到文章ID列表:
添加文章
方便起見,以node-redis添加hash為例:
client.hmset('article:001', { title: 'test1', content: '....', keywords: 'redis,技術' })
client.hmset('article:002', { title: 'test2', content: '..', keywords: 'redis' })
client.hmset('article:003', { title: 'test3', content: '....', keywords: 'redis,技術' })
client.hmset('article:004', { title: 'test4', content: '..', keywords: '技術' })
創建索引
zadd keyword:redis 1540736588833 001 1540736588833 002 1540736588833 003
zadd keyword:技術 1540736588833 001 1540736588833 003 1540736588833 004
1540736588833是權重值,是當前時間的毫秒值,代表什么時侯添加的這些關鍵字。
連接查詢
ZINTERSTORE out 2 keyword:技術 keyword:redis
此時out中就會存放包含有技術和redis兩個關鍵字的文章ID,即 001 和 003
只更新不存在的索引
有時侯,我們可能在構建索引時不影響原有索引的權重值,以此來保留每個關鍵字最初添加時的時間(權重分數)。以此來統計某個時間段添加此關鍵字的文章。
比如article:004添加了新的關鍵字redis,而且是和“技術”關鍵字一起提交的,此時會更新索引:
zadd keyword:技術? 1550736588800 004
zadd keyword:redis 1550736588800 004
但是我們不希望 keyword:技術 的權重更新,因為此關鍵字已經存在了,則直接使用 NX 即可:
zadd keyword:技術? ?nx? 1550736588800 004
zadd keyword:redis? nx? 1550736588800 004
然后比如說現在想提取昨天之前添加的“技術“文章ID,則直接按score權重查詢即可:
zrangebyscore?keyword:技術 0 1550736588800
這在某些場景中非常有用,比如說銷售給某些客戶添加了“無意向客戶“標簽,后來在銷售的努力下將其轉化成了“潛在客戶“,之后又轉化成了“簽單客戶”,為了考核銷售員業績,?需要統計每周/每月的轉化個數,可以用此種方法可計算某個時間段內添加該標簽的客戶ID。
還有一些其他的參數:
XX: 僅僅更新存在的成員,不添加新成員。
NX: 不更新存在的成員。只添加新成員。
CH: 修改返回值為發生變化的成員總數,原始是返回新添加成員的總數 (CH 是 changed 的意思)。更改的元素是新添加的成員,已經存在的成員更新分數。 所以在命令中指定的成員有相同的分數將不被計算在內。注:在通常情況下,ZADD返回值只計算新添加成員的數量。
INCR: 當ZADD指定這個選項時,成員的操作就等同ZINCRBY命令,對成員的分數進行遞增操作。
同樣可以使用XX來更新只存在的成員,可在一些特殊場景中使用。
分析 t_zset.c 的源碼可知,這些參數是可以一起使用的,比如incr和XX/NX同時使用:
/* Parse options. At the end 'scoreidx' is set to the argument position
* of the score of the first score-element pair. */
scoreidx = 2;
while(scoreidx < c->argc) {
char *opt = c->argv[scoreidx]->ptr;
if (!strcasecmp(opt,"nx")) flags |= ZADD_NX;
else if (!strcasecmp(opt,"xx")) flags |= ZADD_XX;
else if (!strcasecmp(opt,"ch")) flags |= ZADD_CH;
else if (!strcasecmp(opt,"incr")) flags |= ZADD_INCR;
else break;
scoreidx++;
}
/* Turn options into simple to check vars. */
int incr = (flags & ZADD_INCR) != 0;
int nx = (flags & ZADD_NX) != 0;
int xx = (flags & ZADD_XX) != 0;
int ch = (flags & ZADD_CH) != 0;
總結
以上是生活随笔為你收集整理的redis zset转set 反序列化失败_Redis只往zset有序集合添加不存在的数据:关键字索引查询构建+源码分析...的全部內容,希望文章能夠幫你解決所遇到的問題。
- 上一篇: 微软计划在 Win11 开始菜单中引入小
- 下一篇: 保值换新是什么意思