您的位置:首页 > 编程语言 > Python开发

python的TypeError: unhashable type(list/set/dict)问题

2017-05-17 11:36 1141 查看
今天在使用python处理一个列表时,遇到这样一个问题,列表里面的元素都是列表,我想把它去重,于是使用set处理一下,但是出现了这个error。

后来查了一下,原因是因为list是不能哈希的。

这一异常通常出现在,调用 set(…) 来构造一个 set (集合类型)时,set() 需要传递进来可哈希的元素(hashable items)。

(1)list、set、dict:是不可哈希的
>>> list.__hash__
None
>>> set.__hash__
None
>>> dict.__hash__
None
1
2
3
4
5
6
1
2
3
4
5
6

(2)int、float、str、tuple:是可以哈希的
>>> int.__hash__
<slot wrapper '__hash__' of 'int' objects>
>>> float.__hash__
<slot wrapper '__hash__' of 'float' objects>
>>> str.__hash__
<slot wrapper '__hash__' of 'str' objects>
>>> tuple.__hash__
<slot wrapper '__hash__' of 'tuple' objects>
1
2
3
4
5
6
7
8
1
2
3
4
5
6
7
8

(3)list 不使用 hash 值进行索引,故其对所存储元素没有可哈希的要求;set / dict 使用 hash 值进行索引,也即其要求欲存储的元素有可哈希的要求。
>>> set([[], [], []])
TypeError: unhashable type: 'list'
>>> set([{}, {}, {}])
TypeError: unhashable type: 'dict'
>>> set([set(), set(), set()])
TypeError: unhashable type: 'set'
1
2
3
4
5
6
1
2
3
4
5
6

(4)dict 仅对键(key)有可哈希的要求,对值(value)无此要求。
>>> dict([[["zhangsan", "lisi"], 20]])
TypeError: unhashable type: 'list'
1
2
1
2

注:可能你会问,set 不是可以接受 list,并将其转换为 set 吗?比如
set([1, 2, 3])
,注意,上文说的可哈希,不可哈希,是对可迭代类型(iterables)所存储元素(elements)的要求,
[1,
2, 3]
是可迭代类型,其存储元素的类型为
int
,是可哈希的,如果
set([[1,
2], [3, 4]])
[[1, 2], [3, 4]]
list of lists(list 构成的 list)自然是可迭代的,但其元素为 
[1,
2]
 和 
[3, 4]
是不可哈希的。


为什么 list 是不可哈希的,而 tuple 是可哈希的

(1)因为 list 是可变的在它的生命期内,你可以在任意时间改变其内的元素值。

(2)所谓元素可不可哈希,意味着是否使用 hash 进行索引

(3)list 不使用 hash 进行元素的索引,自然它对存储的元素有可哈希的要求;而 set 使用 hash 值进行索引。

参考链接
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签: