Redis:按分数排序的集合的交集

时间:2015-05-04 14:25:58

标签: node.js google-app-engine redis node-redis sortedset

我想在Redis数据存储区中存储位置三元组,但也想让它们可搜索。这样就可以进行范围查询,例如'给我1点<点数。 x 3和y> 2&#39 ;.因此,我使用了有组合的组合。

每个三元组都保存在Redis中(例如,位置A,x = 1,y = 2,z = 3):

hset /locations/A x "1"
hset /locations/A y "2"
hset /locations/A z "3"
hset /locations/A payload "{ ...some json payload... }"
zadd /locations:x 1 locations/A
zadd /locations:y 2 locations/A
zadd /locations:z 3 locations/A

通过这种方式,我可以轻松找到所有位置(或指向位置的路径),例如x值介于4和5之间:

zrangebyscore /locations:x 4 5

或所有地点,例如y值介于1和3之间:

zrangebyscore /locations:x 1 3

当我尝试匹配所有位置的x值介于4和5之间且y值介于1和3之间时会出现问题,因为那时我必须对Redis进行两次查询,然后将这些值与NodeJS中的Javascript进行比较,当定义了很多位置时,这可能非常耗时。有人遇到过这样的问题吗?

我尝试了zinterstore和zunionstore,但尚未找到令人满意的解决方案。我考虑将zrangebyscores存储到一个临时集中然后做一个zinterstore,但是没有找到Redis命令将zrangebyscore的输出直接存储到Redis(在同一个命令中)。

2 个答案:

答案 0 :(得分:2)

我想忽略用例(位置路径/距离)本身,因为有多种经过验证的方法可以解决这一挑战,也可以使用Redis(搜索地理空间,你们会找到),然后专注于技术

因此,假设您要发明并实施自己的地理逻辑,最有效的方法(不修改Redis'代码)来解决评分/测距/交叉/中涉及的挑战......这些排序集将位于Lua脚本中。这就是你可能会流行的称呼"数据重力" - 处理器接近数据,因此访问和操作数据的速度最快,无需网络。

在这些脚本中,您可以将ZRANGEBYSCORE的结果存储在局部变量中,执行您需要执行的任何操作,并使用它们,并将最终结果回复给(Node.js)客户端。

答案 1 :(得分:0)

做到这一点,做你的两个问题,Redis是快速的,并不关心。然后javascript Simplest code for array intersection in javascript找到两者中存在的值。