繁体   English   中英

在迭代过程中,在Python中添加新密钥或附加到字典中的旧密钥的最有效方法是什么?

[英]Most efficient way to add new keys or append to old keys in a dictionary during iteration in Python?

在不同来源的字典中编译数据时,这是一种常见情况:

假设你有一个存储事物列表的字典,比如我喜欢的东西:

likes = {
    'colors': ['blue','red','purple'],
    'foods': ['apples', 'oranges']
}

和第二个字典,其中包含一些相关的值:

favorites = {
    'colors':'yellow',
    'desserts':'ice cream'
}

然后,您想迭代“favorites”对象,并使用“likes”字典中的相应键将该对象中的项目附加到列表中,或者向其添加一个新键,其值为包含“in”中值的列表最爱”。

做这件事有很多种方法:

for key in favorites:
    if key in likes:
        likes[key].append(favorites[key])
    else:
        likes[key] = list(favorites[key])

要么

for key in favorites:
    try:
        likes[key].append(favorites[key])
    except KeyError:
        likes[key] = list(favorites[key])

还有更多......

我通常使用第一种语法,因为它感觉更加pythonic,但如果还有其他更好的方法,我很想知道它们是什么。 谢谢!

使用collections.defaultdict ,其中默认值是新的list实例。

>>> import collections
>>> mydict = collections.defaultdict(list)

通过这种方式,调用.append(...)将始终成功,因为如果存在不存在的键,则将在新的空列表上调用append

您可以使用之前生成的列表来实例化defaultdict ,以防您从其他来源获得dict likes ,如下所示:

>>> mydict = collections.defaultdict(list, likes)

请注意,使用list作为defaultdictdefault_factory属性也会在文档中作为示例进行讨论。

使用collections.defaultdict:

import collections

likes = collections.defaultdict(list)

for key, value in favorites.items():
    likes[key].append(value)

defaultdict采用单个参数,一个工厂,用于根据需要为未知键创建值。 list是一个这样的函数,它创建空列表。

迭代.items()将使您无需使用密钥来获取值。

除了defaultdict,常规字典提供了一种可能性(可能看起来有点奇怪): dict.setdefault(k[, d])

for key, val in favorites.iteritems():
    likes.setdefault(key, []).append(val)

谢谢代表+20 - 我从1989年到2009年30秒。 让我们记住,自从沃尔在欧洲倒台已有20年了。

>>> from collections import defaultdict
>>> d = defaultdict(list, likes)
>>> d
defaultdict(<class 'list'>, {'colors': ['blue', 'red', 'purple'], 'foods': ['apples', 'oranges']})
>>> for i, j in favorites.items():
    d[i].append(j)

>>> d
defaultdict(<class 'list'>, {'desserts': ['ice cream'], 'colors': ['blue', 'red', 'purple', 'yellow'], 'foods': ['apples', 'oranges']})

所有的答案都是defaultdict ,但我不确定这是最好的方法。 defaultdict给予期望dict的代码可能很糟糕。 (请参阅: 如何为无意识的客户提供默认安全信息? )我个人对此事感到非常伤心。 (我实际上发现这个问题寻找“哪个更好, dict.get()defaultdict ”的答案。)另一个线程中有人说如果你不想一直这样做,你不想要一个defaultdict ,这可能是真的。 为方便起见,使用defaultdict可能是错误的方法。 我认为这里有两个需要混淆:

“我想要一个默认值为空列表的字典。” defaultdict(list)是正确的解决方案。

“如果该密钥存在,我想要附加到该密钥列表中,如果它不存在则创建一个列表。” 带有append() my_dict.get('foo', []) append()就是答案。

你们有什么感想?

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM