比较两个列表并从一个列表覆盖/追加到另一个列表

时间:2016-01-23 11:11:05

标签: python list

我正在尝试比较python中的两个列表,并将部分匹配从一个覆盖到另一个,或添加任何新内容。例如:

new_list:

Jason £420
Adam £205
Emma £670
Tim £900
Penny £120
Ed £470

old_list:

Jason £200
Adam £205
Alex £400
Emma £600
Penny £120

我正在尝试更新old_list上的项目,如果它们与new_list(例如Jason)不同,添加新项目(例如Tim),并保留不在new_list中的旧项目(例如Alex),得到像这样:

Jason £420
Adam £205
Alex £400
Emma £670
Penny £120
Tim £900
Ed £470

我一直试图用for循环来做这件事,但我想我已经卡住了。到目前为止得到了这个:

for x, y in enumerate(old_list):
        for z in new_list:
                if z.split(" ")[0] in y:
                        old_list[x] = z
                elif z.split(" ")[0] not in old_list:
                        old_list.append(z)
                else:
                        pass

3 个答案:

答案 0 :(得分:3)

您可以使用dict,但是如果您需要保留订购列表中的元素,可以使用OrderedDict,如下所示:

from collections import OrderedDict

old_d = OrderedDict({'John': 100, 'Marie': 200})
new_d = OrderedDict({'John': 100, 'Marie': 400})  # Marie changes here

# important part, update keys from old_d with values of new_d
# also adds new key-value from new_d
old_d.update(new_d)  # update keys 

print(old_d)  # OrderedDict([('John', 100), ('Marie', 400)])
your_final_list = old_d.items()

答案 1 :(得分:2)

关注为什么 dict这里的正确答案是检查dict.update()方法的文档:https://docs.python.org/2/library/stdtypes.html#dict.update

  

使用其他覆盖的键/值对更新字典   现有密钥。

这正是您正在寻找的行为:

old_dict = {"Jason": 200, "Emma": 40}
new_dict = {"Tim": 10, "Jason": 420 }

old_dict.update( new_dict )
print old_dict
{"Jason": 420, "Emma": 40, "Tim": 10}

如果您需要按特定顺序访问元素,那么在sorted()上使用old_dict.keys()可以为您提供足够的可能性来实现您可能拥有的任何排序需求。

答案 2 :(得分:1)

使用dict解决问题要好得多,但使用list解决map

names_old = list(map(lambda x: x.split()[0], old_list))
names_new = list(map(lambda x: x.split()[0], new_list))

for x, y in enumerate(names_new):
    item = new_list[names_new.index(y)]
    if y in names_old:
        old_list[names_old.index(y)] = item
    else:
        old_list.append(item)

In [676]: old_list
Out[676]: 
['Jason £420',
 'Adam £205',
 'Alex £400',
 'Emma £670',
 'Penny £120',
 'Tim £900',
 'Ed £470']