2012-07-01 77 views
4

我使用redis为我的web应用程序实现社交流和通知系统。我是redis的新手,对散列和效率有一些疑问。redis - 使用哈希

我读过这个真棒Instagram post 我计划实施他们类似的解决方案以实现最小的存储。

在他们的博客中提到,他们不喜欢这样

取散型的优势,我们斗了所有介质ID为1000桶(我们只取ID,除以1000,并丢弃其余的)。这决定了我们陷入的关键;接下来,在生存在该密钥的散列内,媒体ID是散列中的查找键,并且用户ID是该值。一个实例中,给定的1155315媒体ID,这意味着它落入桶1155(千分之一百十五万五千三百十五= 1155):在一个

HSET "mediabucket:1155" "1155315" "939" 
HGET "mediabucket:1155" "1155315" 
> "939" 

所以代替具有1000单独键它们存储它的与千位查找键的散列。我的疑问是为什么我们不能将查找关键值增加到更大。

例如:Media ID of 1155315 will fall into mediabucket:115 by dividing it by 10000 甚至更​​大。

他们为什么用一个带有1000个查找键的哈希桶来解决问题。为什么他们不能有一个哈希桶与100000查找键。是否与效率有关?

我需要你的建议在我的web应用程序中实现高效的方法。

P.S.请!不要说,stackoverflow不是提问的建议,我不知道在哪里可以找到帮助。

谢谢!

回答

6

是的,这与效率有关。

我们问总是有帮助的彼得Noordhuis,Redis的的核心开发者之一,投入,他建议我们使用Redis的哈希值。 Redis中的哈希是可以非常有效地编码在内存中的字典; Redis设置'hash-zipmap-max-entries'配置哈希可以有效编码的最大条目数。我们发现这个设置最好在1000左右;任何更高和HSET命令会导致明显的CPU活动。有关更多详细信息,可以查看zipmap源文件。

小哈希以特殊方式编码(zipmaps),这是内存有效的,但操作O(N)而不是O(1)。因此,使用一个带有100k字段的zipmap而不是100个带有1k字段的zipmap,您无​​法获得内存优势,但所有操作的速度都会降低100倍。

+0

谢谢,所以我会去1000 :) – rnk

2

基本上,他们希望单个散列中存储的值的数量不超过1000.他们可能会将其Redis实例配置设置为与该数字很好地配合使用(您的设置为hash-zipmap-max-entries)。

每次哈希将超过指定的元素或元素大小的数量时,它将被转换为真正的哈希表,并且内存保存将会丢失。

- http://redis.io/topics/memory-optimization

据我了解,你的问题是 “到底为什么1000,而不是更多吗?”那是因为他们必须在空间效率和速度之间进行选择。空间高效表示的操作复杂度为O(N),而不是O(1)作为正常哈希值 - 它是慢N倍,但占用较少的内存。

他们测试了不同的值,发现1000是一个很好的折中解决方案 - 占用空间不大,但仍然足够快。

+0

谢谢,所以我会去1000 :) – rnk

+1

@rnk你可以测试哪个值最适合你的任务。 – scriptin