Redis:如何将“普通”集与排序集相交?

时间:2012-05-08 14:33:40

标签: redis

假设我有一个集合(或排序集或列表,如果那样更好) A 为100到1000个字符串。

然后我有一个排序集 B 的更多字符串,比如一百万。

现在 C 应该是 A B (当然是字符串)的交集。

我想要每个元组(X,SCORE_OF_X_IN_B),其中X在 C 中。

任何想法?

我有两个想法:

  1. Interstore
    • 存储一个排序集,每个得分为0
    • interstore to D
    • 获取D
    • 的每一项
    • 删除D
  2. 客户端中的简单循环
    • 在我的客户端程序中循环A
    • 获取每个字符串的zscore
  3. 虽然1.在redis方面有太多的开销(例如必须写。重写页面表明相当高的时间复杂度,http://redis.io/commands/zinterstore),2。会有| A |数据库连接并不是一个好的选择。

    也许我可以编写一个redis / lua脚本,它可以像zscore一样工作但是有任意数量的字符串,但我不确定我的主机是否允许脚本......

    所以我只是想问一下,如果有一个优雅而快速的解决方案可用而无需编写脚本!

1 个答案:

答案 0 :(得分:37)

您的问题有一个简单的解决方案:ZINTERSTORE可以使用SETZSET。尝试:

redis> sadd foo a
(integer) 1
redis> zadd bar 1 a
(integer) 1
redis> zadd bar 2 b
(integer) 1
redis> zinterstore baz 2 foo bar AGGREGATE MAX
(integer) 1
redis> zrange baz 0 -1 withscores
1) "a"
2) "1"

修改:我在上面添加了AGGREGATE MAX,因为redis会为(未分类的)集foo的每个成员提供默认分数1,和SUM在(已排序)集bar中得到的任何分数。