gpt4 book ai didi

python - 散列生成器表达式

转载 作者:太空狗 更新时间:2023-10-30 00:43:37 25 4
gpt4 key购买 nike

显然 python 将允许我散列生成器表达式,如 (i for i in [1, 2, 3, 4, 5])

>>> hash(i for i in [1, 2, 3, 4, 5])
8735741846615

然而,仔细检查后,无论我将什么生成器放入该哈希值,该哈希值始终相同!

>>> hash(i for i in range(2))
8735741846615
>>> hash(i for i in [1, 2, 3, 4, 5, 6])
8735741846615
>>> hash(i for i in [0, 1, 2, 3, 4, 5, 6])
8735741846615

为什么会这样?为什么甚至允许对生成器进行哈希处理?

我需要这样做,因为我要将内容存储在字典缓存中。您可以通过传递对象列表来访问缓存中的条目。但是具有不同项目的某些列表组仍应指向相同的条目,因为这里唯一重要的是每个列表项目中一个属性的整数值。因此,它们应该仅基于这些整数值进行哈希处理,而不是与项目本身相关的任何内容,以避免不必要的缓存未命中。

我知道你总是可以将表达式转换为元组,但我想问你是否可以通过简单地使用没有元组容器的生成器的输出来绕过它,类似于 sum() 可以用于这样的事情。

最佳答案

所以这里其实有两个问题:

  1. 为什么生成器有哈希,例如名单没有?
  2. 为什么总是得到相同的哈希?

对于 2,答案很简单:在这种情况下,哈希基于对象的 id。由于您实际上并不存储该对象,因此它的内存会被重用。这意味着下一个生成器具有相同的 id 和哈希值。

对于 1,答案是“因为他们可以”。 hash 主要用于 dictset 和其他允许识别对象的情况。这些情况设置了 a == b 也意味着 hash(a) == hash(b) 的约束(反之不受约束)。

现在,对于listdict等集合,平等是基于内容的。例如,[1,2,3] == [1,2,3] 不管它们是否是相同的对象。这意味着如果向它们添加某些内容,它们的相等性会发生变化,因此它们的 hash 也会发生变化。因此,hash 是未定义的,因为它必须是常量才能在 dict 等中工作。

相比之下,生成器可以有任何内容。例如,考虑一个提供随机值的生成器。因此,按内容比较生成器是没有意义的。他们只是通过身份进行比较。因此,对于生成器,a == b 等于 id(a) == id(b)。反过来,这意味着基于 id(a)hash(a) 将始终通过对 hash 的相等性来满足约束。

关于python - 散列生成器表达式,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/38174211/

25 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com