字典在Python 3.6中排序(至少在CPython实现下),与之前的版本不同.这似乎是一个重大变化,但它只是文档中的一小段.它被描述为CPython实现细节而不是语言特性,但也暗示这可能成为未来的标准.
在保留元素顺序的同时,新字典实现如何比旧字典实现更好?
以下是文档中的文字:
dict()
现在使用PyPy开创的"紧凑"表示.与Python 3.5相比,新dict()的内存使用量减少了20%到25%.PEP 468(在函数中保留**kwargs的顺序.)由此实现.这个新实现的顺序保留方面被认为是一个实现细节,不应该依赖(这可能会在未来发生变化,但是在更改语言规范之前,希望在几种版本的语言中使用这个新的dict实现为所有当前和未来的Python实现强制命令保留语义;这也有助于保持与随机迭代顺序仍然有效的语言的旧版本的向后兼容性,例如Python 3.5).(由INADA Naoki在issue 27350中提供.最初由Raymond Hettinger提出的想法.)
2017年12月更新:Python 3.7 保证了dict
保留插入顺序
我正在玩OrderedDict
Python 3.6中的类型,并且对它的行为感到惊讶.当我dict
在IPython中创建这样的简单时:
d = dict([('sape', 4139), ('guido', 4127), ('jack', 4098)])
Run Code Online (Sandbox Code Playgroud)
我明白了:
{'guido': 4127, 'jack': 4098, 'sape': 4139}
Run Code Online (Sandbox Code Playgroud)
作为输出,由于某种原因,它不会在实例化时保留元素的顺序.现在,当我创建一个OrderedDict
从d
这样的:
od = OrderedDict(d)
Run Code Online (Sandbox Code Playgroud)
输出是:
OrderedDict([('sape', 4139), ('guido', 4127), ('jack', 4098)])
Run Code Online (Sandbox Code Playgroud)
现在我问自己,OrderedDict
-constructor 如何知道实例化时元素的顺序d
?并且它总是表现相同,这样我可以依赖于元素的顺序OrderedDict
吗?
我已经阅读了关于字典和OrderedDict
s 的Python文档,但我没有找到我的问题的答案.
来自(sys.version
)的输出:
In[22]: sys.version
Out[22]: '3.6.1 (default, Apr 4 2017, 09:40:21) \n[GCC 4.2.1 Compatible Apple LLVM 8.1.0 (clang-802.0.38)]'
Run Code Online (Sandbox Code Playgroud) Python 3 的默认散列函数不是确定性的(hash(None) 因运行而异),甚至没有尽最大努力以高概率生成唯一 id(hash(-1)==hash( -2) 是真的)。
是否有其他一些散列函数可以很好地作为校验和(即两个数据结构散列到相同值的概率可以忽略不计,并且每次运行 python 都返回相同的结果),并且支持所有 python 的内置数据类型,包括无?
理想情况下,它将在标准库中。我可以腌制对象或获取字符串表示,但这似乎不必要,并且浮点数的字符串表示可能是非常糟糕的校验和。
我在标准库中找到了加密哈希 (md5,sha256),但它们只对字节串进行操作。
Haskell 似乎在他们的标准库中得到了这个 ~ 几乎是正确的......但是“Nothing::Maybe Int”和 0 都散列到 0,所以它也不完美。