Python 3将地图字典更新方法更新为其他字典列表

Python 3 map dictionary update method to a list of other dictionaries

本问题已经有最佳答案,请猛点这里访问。

在Python2中,我可以执行以下操作:

1
2
3
4
5
>> d = {'a':1}
>> extras = [{'b':2}, {'c':4}]
>> map(d.update, extras)
>> d['c']
>> 4

在python 3的get a KeyError中:

1
2
3
4
5
>> d = {'a':1}
>> extras = [{'b':2}, {'c':4}]
>> map(d.update, extras)
>> d['c']
>> KeyError: 'c'

我希望在python3中实现与在python2中相同的行为。

我知道python3中的map将返回一个迭代器(lazy evaluation和whatnot),它必须被迭代才能更新字典。

我假设d['c']键查找会以某种方式触发映射迭代,但事实并非如此。

是否有一种不需要编写for循环就可以实现这种行为的方法?与地图相比,我觉得这很冗长。

我考虑过使用列表理解:

1
2
3
4
5
>> d = {'a':1}
>> extras = [{'b':2}, {'c':4}]
>> [x for x in map(d.update, extras)]
>> d['c']
>> 4

但它看起来不像是Python。


值得注意的是,Python中的3 map创建迭代器,这是不是在本身的原因和发生的任何updates到):

1
2
3
4
5
6
>>> d = {'a': 1}
>>> extras = [{'b':2}, {'c':4}]
>>> map(d.update, extras)
<map object at 0x105d73c18>
>>> d
{'a': 1}

map强行被完全评估,你可以通过它的list明确:

1
2
3
4
>>> list(map(d.update, extras))
[None, None]
>>> d
{'a': 1, 'b': 2, 'c': 4}

然而,有关的部分是它的新Python中的3倍。

Particularly tricky is map() invoked for the side effects of the
function; the correct transformation is to use a regular for loop
(since creating a list would just be wasteful).

在你的案例,这将看起来像:

1
2
for extra in extras:
    d.update(extra)

这是不是在一个不必要的None结果列表。


alongside"的解释是"jonrsharpe explains明确的问题,你可以使用Python中的3 collections.ChainMap这样的任务:

1
2
3
4
5
6
>>> from collections import ChainMap
>>> chain=ChainMap(d, *extras)
>>> chain
ChainMap({'a': 1}, {'b': 2}, {'c': 4})
>>> chain['c']
4

但是请注意,如果有重复的键,从第一个映射值,得到使用。

阅读更多关于《优势:利用chainmap collections.chainmap的目的是什么?