Yug*_*dle 4 python class subclass immutability
我想subclass
dict
在python中使子类的所有字典都是不可变的.
我不明白如何__hash__
影响不变性,因为在我的理解中它只是表示对象的相等或不相等!
那么,可以__hash__
用来实现不变性吗?怎么样 ?
更新:
目标是来自API的常见响应可用作dict,必须作为全局变量共享.那么,无论如何都需要完好无损?
Kon*_*nin 29
可以immutable dict
仅使用标准库来创建。
from types import MappingProxyType
power_levels = MappingProxyType(
{
"Kevin": 9001,
"Benny": 8000,
}
)
Run Code Online (Sandbox Code Playgroud)
Mar*_*lla 16
在freezedict中,哈希是按照 Victor Stinner 拒绝的PEP 416简单实现的:
def __hash__(self):
try:
fs = frozenset(self.items())
except TypeError:
hash = -1
else:
hash = hash(fs)
if hash == -1:
raise TypeError(f"not all values are hashable: '{self.__class__.__name__}'")
return hash
Run Code Online (Sandbox Code Playgroud)
关于哈希性和平等性,它们是不一样的。
即使两个对象是可变的,它们也可以是相等的。
例如,{1:2, 3:4} == {3:4, 1:2}
通常,可哈希对象是不可变的,但这不是必需的。
此外,通常具有相同哈希值的对象也是相等的,但这并不总是正确的。
例如,hash(-1) == hash(-2) == -2
。
这称为哈希冲突。
进一步阅读:
https://docs.python.org/3/glossary.html#term-hashable
https://en.wikipedia.org/wiki/Hash_collision
PS:我是该软件包的新维护者frozendict
。
我找到了一个官方参考:
class imdict(dict):
def __hash__(self):
return id(self)
def _immutable(self, *args, **kws):
raise TypeError('object is immutable')
__setitem__ = _immutable
__delitem__ = _immutable
clear = _immutable
update = _immutable
setdefault = _immutable
pop = _immutable
popitem = _immutable
Run Code Online (Sandbox Code Playgroud)
归因:http://www.python.org/dev/peps/pep-0351/
从 Python 3.3 开始,可以用来MappingProxyType
创建不可变映射:
>>> from types import MappingProxyType
>>> MappingProxyType({'a': 1})
mappingproxy({'a': 1})
>>> immutable_mapping = MappingProxyType({'a': 1})
>>> immutable_mapping['a']
1
>>> immutable_mapping['b'] = 2
Traceback (most recent call last):
(...)
TypeError: 'mappingproxy' object does not support item assignment
Run Code Online (Sandbox Code Playgroud)
它不可散列,因此您不能将其用作字典键(并且它是“最终”键,因此您不能将其子类化以覆盖__hash__
),但如果您想要一个不可变的映射来防止意外修改全局值,那么它就足够了(就像类的默认属性)。
小心不要添加本身可以修改的可变值。
那么,可以
__hash__
用来实现不变性吗?
不,它不能.无论其__hash__
方法如何,对象都可以变得可变(或不变).
不可变对象之间的关系__hash__
是,由于无法更改不可变对象,因此返回的值在__hash__
构造后保持不变.对于可变对象,这可能是也可能不是这种情况(推荐的做法是这样的对象根本无法哈希).
有关进一步的讨论,请参阅问题13707:澄清合hash()
规期.
归档时间: |
|
查看次数: |
5574 次 |
最近记录: |