获取具有不同子列表数据类型的列表元素的交集

Get intersection of list elements with different sublist datatypes

我有两个列表,其中包含列表元素,例如:

list1 = [['placeholder1', {'data': 'data1'}], ['placeholder2', {'data': 'data2'}], ['placeholder2', {'data': 'data1'}]]
list2 = [['placeholder2', {'data': 'data2'}], ['placeholder3', {'data': 'data5'}]]

intersection_result = [['placeholder2', {'data': 'data2'}]]

子列表元素的结构只是一个例子。也可能发生所有子列表元素都包含字符串 ['asdf', 'qwert'] 或字符串和数字的混合 ['sdfs', 232]。但是,子列表结构始终相同(在两个列表中)。

如何获取两个列表中相同的列表元素的交集?

如果我的理解是正确的,您可以通过检查和 selecting any() 最小列表中的元素与较大列表中的元素相等来获得交集。

有了理解,这看起来像这样:

intersection_res = [l for l in min(list2, list1, key=len) if any(l == l2 for l2 in max(list1, list2, key=len))]

这使用 min and max with a key assigned to len 始终从较小的列表中 select 并检查较大的列表。

这产生:

print(intersection_res)
[['placeholder2', {'data': 'data2'}]]

如果您预先分配最小-最大列表,或者当然,如果您始终确定哪个列表大于另一个,则可以减少这种理解:

sm, la = list1, list2 if len(list1) < len(list2) else list2, list1
intersection_res = [l for l in sm if any(l == l2 for l2 in la)]

一个简单的解决方案,独立于您的数据结构。 您可以为数据生成 signature hashes(使用 json 或 pformat),并在 list1 和 list2 中找到共同的哈希值。

演示 : http://ideone.com/5i9cs8

import json

list1 = [['placeholder1', {'data': 'data1'}], ['placeholder2', {'data': 'data2'}], ['placeholder2', {'data': 'data1'}]]
list2 = [['placeholder2', {'data': 'data2'}], ['placeholder3', {'data': 'data5'}]]
sig1 = { hash(json.dumps(x, sort_keys=True)):x for x in list1 }
sig2 = { hash(json.dumps(x, sort_keys=True)):x for x in list2 }
result = {x:sig1[x] for x in sig1 if x in sig2}
print(result)
#prints {-7754841686355067234: ['placeholder2', {'data': 'data2'}]}
  • 如果您的词典有不支持 json 序列化的数据,例如datetime, pformat 可以很好地工作,或者你可以使用 cPickle,str 也适用于简单的情况。您可以根据您的数据集和所需的效率做出选择。