Python字典:基于公共键和值的键值对分组

2024-09-25 08:31:10 发布

您现在位置:Python中文网/ 问答频道 /正文

我有一个列表,里面有这样的字典:

list1 = [{'name': 'bob', 'email': 'bob@bob.com', 'address': '123 house lane', 
'student_id': 12345}, {'name': 'steve', 'email': 'steve@steve.com',
'address': '456 house lane', 'student_id': 34567}, {'name': 'bob',
'email': 'bob2@bob2.com', 'address': '789 house lane', 'student_id': 45678}]

python中有没有一种方法可以根据“name”值在新字典中对选定的键、值对进行分组?例如,最终结果是:

^{pr2}$

Tags: 方法namecomid列表字典addressemail
2条回答

下面的代码为您提供嵌套字典。嵌套字典使您能够更快地处理查找键,而在list中则必须创建循环。在

list1 = [{'name': 'bob', 'email': 'bob@bob.com', 'address': '123 house lane', 
'student_id': 12345}, {'name': 'steve', 'email': 'steve@steve.com',
'address': '456 house lane', 'student_id': 34567}, {'name': 'bob',
'email': 'bob2@bob2.com', 'address': '789 house lane', 'student_id': 45678}]

dict1 = {}
for content in list1:
    if content['name'] in [name for name in dict1]:
        dict1[content['name']] = {'emails': dict1[content['name']]['emails'] + [content['address']], 'addresses': dict1[content['name']]['addresses'] + [content['email']]}
    else:
        dict1[content['name']] = {'emails': [content['email']], 'addresses': [content['address']]}
print dict1

代码的输出是

^{pr2}$

听起来这就是你想做的:

list1 = [{'name': 'bob', 'email': 'bob@bob.com', 
          'address': '123 house lane', 'student_id': 12345},
         {'name': 'steve', 'email': 'steve@steve.com',
          'address': '456 house lane', 'student_id': 34567},
         {'name': 'bob', 'email': 'bob2@bob2.com',
          'address': '789 house lane', 'student_id': 45678}]

import operator
list1.sort(key=operator.itemgetter('name'))

new_list = []
for studentname, dicts in itertools.groupby(list1, operator.itemgetter('name')):
    d = {'name': studentname}
    for dct in dicts:
        for key,value in dct.items():
            if key == 'name':
                continue
            d.setdefault(key, []).append(value)
    new_list.append(d)

演示:

^{pr2}$

如果您打算广泛地使用它,您可能应该硬编码一些更好的名称(例如,addresses而不是address),并创建一个映射来填充它们。在

keys_mapping = {'address': 'addresses',
                'email': 'emails',
                'student_id': 'student_ids'}

for studentname, dicts in itertools.groupby(list1, operator.itemgetter('name')):
    d = {'name': studentname}
    for dct in dicts:
        for key,value in dct_items():
            new_key = keys_mapping.get(key,key)
            # get the updated value if it's defined, else give `key`
            d.setdefault(new_key, []).append(value)
    new_list.append(d)

相关问题 更多 >