我了解为什么包含nuts['Price'] = nuts['Type'].map(pricedf['Type'])
之类的可变对象的tuple
不能被散列,因为元组中的list
个项目仍然可以更新。
示例:
list
这是不可散列的:
# hashable
tuple_test = (1,2,3)
print(tuple_test.__hash__())
以上对我来说很有意义。
但是当我使用# Not hashable
tuple_test2 = (1,2, [1,2])
print(tuple_test2.__hash__())
个项目创建一个namedtuple
时,它仍然是可散列的:
list
,当我添加# hashable
named_tuple = namedtuple("TestTuple", 'name age')
时:
list
为什么元组和namedtuple之间有这种区别?
答案 0 :(得分:6)
但是当我创建一个带有列表作为项目的namedtuple时,它仍然 可哈希的...
您永远不会那样做。您创建一个具有str
,'adam'
和int
,20
以下内容:
named_tuple = namedtuple("TestTuple", 'name age')
和
named_tuple = namedtuple("TestTuple", ["name", "age"])
不不创建namedtuple
对象,它们创建namedtuple
类。根据{{3}}:
返回一个名为typename的新元组子类。
换句话说,collections.namedtuple
是一个工厂函数,它返回一个 class 。如果创建这些类的实例,则它们的实例与常规tuple
实例遵循相同的规则。
所以请考虑:
>>> from collections import namedtuple
>>> TestTuple = namedtuple('TestTuple', ['name', 'age'])
>>> type(TestTuple)
<class 'type'>
>>> class A: pass
...
>>> type(A)
<class 'type'>
TestTuple,namedtuple
工厂函数的返回值,不是namedtuple实例,它是type
的实例,就像所有其他类一样。
在创建此类的实例时:
>>> test_tuple = TestTuple('adam',32)
>>> type(test_tuple)
<class '__main__.TestTuple'>
它们遵循常规tuple
对象执行的哈希规则:
>>> hash(test_tuple)
5589201399616687819
>>> test_tuple = TestTuple('adam', [32, 31])
>>> hash(test_tuple)
Traceback (most recent call last):
File "<stdin>", line 1, in <module>
TypeError: unhashable type: 'list'
请注意,fieldnames参数可以接受字段名的序列(例如列表),或者为了方便起见,可以接受由空格/逗号分隔的字段名字符串,因此也可以从文档中获取:
... field_names是一系列字符串,例如['x','y']。 另外,field_names可以是单个字符串,每个fieldname 用空格和/或逗号分隔,例如“ x y”或“ x,y”。