Python 3.x python3:了解`setdefault`字典方法的用法
我看到了以下代码片段:Python 3.x python3:了解`setdefault`字典方法的用法,python-3.x,dictionary,Python 3.x,Dictionary,我看到了以下代码片段: # list representing sequence of states states = ['a','b','c','d','a','a','a','b','c','b','b','b'] # matrix of transitions M = {} for i in range(len(states)-1): M.setdefault((states[i], states[i+1]), [0])[0] += 1 因此它遍历列表并计算转换,例如a->b
# list representing sequence of states
states = ['a','b','c','d','a','a','a','b','c','b','b','b']
# matrix of transitions
M = {}
for i in range(len(states)-1):
M.setdefault((states[i], states[i+1]), [0])[0] += 1
因此它遍历列表并计算转换,例如a->b
,b->c
,c->c
等等。我知道setdefault()
会在键不在字典中时插入默认值。但是我不明白为什么默认值是列表本身,在本例中是[0]。另外,M.setdefault(…)[0]
意味着我们总是选择列表中的第一个元素并递增它
这种方法的原因可能是什么?它按照您的理解工作-关于为什么使用列表值而不是直接使用整数-使用“纯”整数和
setdefault(…)
不起作用
原因:设置默认值()返回该键的字典值。如果您返回一个列表,您将获得该列表的引用。如果修改列表,更改将反映在字典中(因为:reference)。如果使用整数,则返回该整数,但修改它不会更改分配给dict中键的值
# list representing sequence of states
states = ['a','b','c','d','a','a','a','b','c','b','b','b']
# matrix of transitions
M = {}
for i in range(len(states)-1):
M.setdefault((states[i], states[i+1]), [0])[0] += 1
print(M)
输出:
{('a', 'b'): 2, ('b', 'c'): 2, ('c', 'd'): 1, ('d', 'a'): 1,
('a', 'a'): 2, ('c', 'b'): 1, ('b', 'b'): 2}
{('a', 'b'): 2, ('b', 'c'): 2, ('c', 'd'): 1, ('d', 'a'): 1,
('a', 'a'): 2, ('c', 'b'): 1, ('b', 'b'): 2}
如果不想使用包含单个计数器整数的列表,可以执行以下操作:
for i in range(len(states)-1):
# does not work, error: M.setdefault((states[i], states[i+1]), 0) += 1
M.setdefault((states[i], states[i+1]), 0)
M[(states[i], states[i+1])] += 1
print(M)
输出:
{('a', 'b'): 2, ('b', 'c'): 2, ('c', 'd'): 1, ('d', 'a'): 1,
('a', 'a'): 2, ('c', 'b'): 1, ('b', 'b'): 2}
{('a', 'b'): 2, ('b', 'c'): 2, ('c', 'd'): 1, ('d', 'a'): 1,
('a', 'a'): 2, ('c', 'b'): 1, ('b', 'b'): 2}
但这需要两行代码——不能直接赋值给整数
我个人可能会:
# list representing sequence of states
states = ['a','b','c','d','a','a','a','b','c','b','b','b']
# matrix of transitions
from collections import defaultdict
M = defaultdict(int)
for a, b in zip(states,states[1:]):
M[(a,b)] += 1
print(dict(M)) # or use M directly - its str-output is not that nice though
哪一个应该比使用基本字典更有效?这不是合法的Python代码。如果不解释这段代码试图实现什么,你希望有人如何解释这个特定的实现?Patrick,谢谢你的全面回答。返回一个列表会得到对该列表的引用——它是Pyhon列表的一个属性,还是任何迭代对象?另外,为什么
M.setdefault((states[i],states[i+1]),0)+=1
失败?@Mark因为原始事物存储列表。您从dict中检索列表引用的副本,并通过它修改两个引用所指向的数据。您的try将返回一个整数的副本-如果您修改它,您不会修改原始的整数,您只需为它的副本分配一个新值。