Python 相当于字典的 zip
声明:本页面是StackOverFlow热门问题的中英对照翻译,遵循CC BY-SA 4.0协议,如果您需要使用它,必须同样遵循CC BY-SA许可,注明原文地址和作者信息,同时你必须将它归于原作者(不是我):StackOverFlow
原文地址: http://stackoverflow.com/questions/16458340/
Warning: these are provided under cc-by-sa 4.0 license. You are free to use/share it, But you must attribute it to the original authors (not me):
StackOverFlow
Python equivalent of zip for dictionaries
提问by Eric
If I have these two lists:
如果我有这两个列表:
la = [1, 2, 3]
lb = [4, 5, 6]
I can iterate over them as follows:
我可以按如下方式迭代它们:
for i in range(min(len(la), len(lb))):
print la[i], lb[i]
Or more pythonically
或者更pythonically
for a, b in zip(la, lb):
print a, b
What if I have two dictionaries?
如果我有两个字典怎么办?
da = {'a': 1, 'b': 2, 'c': 3}
db = {'a': 4, 'b': 5, 'c': 6}
Again, I can iterate manually:
同样,我可以手动迭代:
for key in set(da.keys()) & set(db.keys()):
print key, da[key], db[key]
Is there some builtin method that allows me to iterate as follows?
是否有一些内置方法可以让我按如下方式进行迭代?
for key, value_a, value_b in common_entries(da, db):
print key, value_a, value_b
采纳答案by Volatility
There is no built-in function or method that can do this. However, you could easily define your own.
没有内置函数或方法可以做到这一点。但是,您可以轻松定义自己的。
def common_entries(*dcts):
for i in set(dcts[0]).intersection(*dcts[1:]):
yield (i,) + tuple(d[i] for d in dcts)
This builds on the "manual method" you provide, but, like zip, can be used for any number of dictionaries.
这建立在您提供的“手动方法”之上,但与 一样zip,可用于任意数量的字典。
>>> da = {'a': 1, 'b': 2, 'c': 3}
>>> db = {'a': 4, 'b': 5, 'c': 6}
>>> list(common_entries(da, db))
[('c', 3, 6), ('b', 2, 5), ('a', 1, 4)]
When only one dictionary is provided as an argument, it essentially returns dct.items().
当仅提供一个字典作为参数时,它本质上返回dct.items().
>>> list(common_entries(da))
[('c', 3), ('b', 2), ('a', 1)]
回答by Koreth
You may want to make an intersection, using the Python Set type.
您可能想要使用 Python Set 类型进行交集。
da = {'a': 1, 'b': 2, 'c': 3, 'e': 7}
db = {'a': 4, 'b': 5, 'c': 6, 'd': 9}
dc = set(da) & set(db)
for i in dc:
print i,da[i],db[i]
Cheers,
干杯,
K.
K。
回答by Azat Ibrakov
In case if someone is looking for generalized solution:
如果有人正在寻找通用解决方案:
import operator
from functools import reduce
def zip_mappings(*mappings):
keys_sets = map(set, mappings)
common_keys = reduce(set.intersection, keys_sets)
for key in common_keys:
yield (key,) + tuple(map(operator.itemgetter(key), mappings))
or if you like to separate key from values and use syntax like
或者如果您想将键与值分开并使用类似的语法
for key, (values, ...) in zip_mappings(...):
...
we can replace last line with
我们可以用
yield key, tuple(map(operator.itemgetter(key), mappings))
Tests
测试
from collections import Counter
counter = Counter('abra')
other_counter = Counter('kadabra')
last_counter = Counter('abbreviation')
for (character,
frequency, other_frequency, last_frequency) in zip_mappings(counter,
other_counter,
last_counter):
print('character "{}" has next frequencies: {}, {}, {}'
.format(character,
frequency,
other_frequency,
last_frequency))
gives us
给我们
character "a" has next frequencies: 2, 3, 2
character "r" has next frequencies: 1, 1, 1
character "b" has next frequencies: 1, 1, 2
(tested on Python 2.7.12& Python 3.5.2)
(在Python 2.7.12& 上测试Python 3.5.2)
回答by pylang
Dictionary key viewsare already set-like in Python 3. You can remove set():
字典键视图已经在 Python 3 中类似设置。您可以删除set():
for key in da.keys() & db.keys():
print(key, da[key], db[key])
In Python 2:
在 Python 2 中:
for key in da.viewkeys() & db.viewkeys():
print key, da[key], db[key]
回答by grwlf
Python3: How about the following?
Python3:下面的怎么样?
da = {'A': 1, 'b': 2, 'c': 3}
db = {'B': 4, 'b': 5, 'c': 6}
for key, (value_a, value_b) in {k:(da[k],db[k]) for k in set(da)&set(db)}.items():
print(key, value_a, value_b)
The above snippet prints values of common keys ('b' and 'c') and discards the keys which don't match ('A' and 'B').
上面的代码片段打印了公共键的值('b' 和 'c')并丢弃不匹配的键('A' 和 'B')。
In order to include all keys into the output we could use a slightly modified comprehension: {k:(da.get(k),db.get(k)) for k in set(da)|set(db)}.
为了将所有键都包含在输出中,我们可以使用稍微修改的理解:{k:(da.get(k),db.get(k)) for k in set(da)|set(db)}.

