我正在尝试获取字典列表中所有键的列表,以便填写csv.DictWriter的fieldnames参数。
先前,我有类似的事情:[
{"name": "Tom", "age": 10},
{"name": "Mark", "age": 5},
{"name": "Pam", "age": 7}
]
我正在使用fieldnames = list[0].keys()
获取列表中的第一个字典并提取其密钥。
现在我有类似的东西,其中一个字典有更多的键:值对比其他字典(可能是任何结果)。新密钥是根据来自API的信息动态添加的,因此它们可能会或可能不会出现在每个字典中,而且我事先并不知道会有多少新密钥。
[
{"name": "Tom", "age": 10},
{"name": "Mark", "age": 5, "height":4},
{"name": "Pam", "age": 7}
]
我不能只使用fieldnames = list[1].keys()
,因为它不一定是第二个带有额外键的元素。
一个简单的解决方案是找到具有最多键数的字典并将其用于字段名,但如果您有这样的示例,那将无效:
[
{"name": "Tom", "age": 10},
{"name": "Mark", "age": 5, "height":4},
{"name": "Pam", "age": 7, "weight":90}
]
其中第二个和第三个字典都有3个键,但最终结果应该是列表["name", "age", "height", "weight"]
答案 0 :(得分:51)
all_keys = set().union(*(d.keys() for d in mylist))
编辑:必须解压缩列表。现在修好了。
答案 1 :(得分:16)
您的数据:
>>> LoD
[{'age': 10, 'name': 'Tom'},
{'age': 5, 'name': 'Mark', 'height': 4},
{'age': 7, 'name': 'Pam', 'weight': 90}]
这种理解能够做到:
>>> {k for d in LoD for k in d.keys()}
{'age', 'name', 'weight', 'height'}
它以这种方式工作。首先,创建一个dict键列表列表:
>>> [list(d.keys()) for d in LoD]
[['age', 'name'], ['age', 'name', 'height'], ['age', 'name', 'weight']]
然后创建此列表列表的展平版本:
>>> [i for s in [d.keys() for d in LoD] for i in s]
['age', 'name', 'age', 'name', 'height', 'age', 'name', 'weight']
创建一个消除重复的集合:
>>> set([i for s in [d.keys() for d in LoD] for i in s])
{'age', 'name', 'weight', 'height'}
可以简化为:
{k for d in LoD for k in d.keys()}
答案 2 :(得分:3)
>>> lis=[
{"name": "Tom", "age": 10},
{"name": "Mark", "age": 5, "height":4},
{"name": "Pam", "age": 7, "weight":90}
]
>>> {z for y in (x.keys() for x in lis) for z in y}
set(['age', 'name', 'weight', 'height'])
答案 3 :(得分:2)
以下示例将提取密钥:
set_ = set()
for dict_ in dictionaries:
set_.update(dict_.keys())
print set_
答案 4 :(得分:2)
从@ AshwiniChaudhary的回答中借用lis
,这是对如何解决问题的解释。
>>> lis=[
{"name": "Tom", "age": 10},
{"name": "Mark", "age": 5, "height":4},
{"name": "Pam", "age": 7, "weight":90}
]
直接在dict上迭代返回其键,因此您不必调用keys()
来取回它们,在列表中保存每个元素的函数调用和列表构造。
>>> {k for d in lis for k in d}
set(['age', 'name', 'weight', 'height'])
或使用itertools.chain
:
>>> from itertools import chain
>>> {k for k in chain(*lis)}
set(['age', 'name', 'weight', 'height'])
答案 5 :(得分:2)
from itertools import chain
lis = [
{"name": "Tom", "age": 10},
{"name": "Mark", "age": 5, "height":4},
{"name": "Pam", "age": 7, "weight":90}
]
# without qualification a dict iterates over its keys
# and set takes any iterable in its constructor
headers_as_set = set(chain.from_iterable(lis))
# you asked for a list
headers = list(
set(chain.from_iterable(lis))
)