我想要取两个列表中共同出现的值。
a = [1, 2, 3, 4, 5]
b = [9, 8, 7, 6, 5]
returnMatches(a, b)
比如说,会返回[5]
。
我想要取两个列表中共同出现的值。
a = [1, 2, 3, 4, 5]
b = [9, 8, 7, 6, 5]
returnMatches(a, b)
比如说,会返回[5]
。
虽然不是最有效的方法,但迄今为止最明显的方法是:
>>> a = [1, 2, 3, 4, 5]
>>> b = [9, 8, 7, 6, 5]
>>> set(a) & set(b)
{5}
如果顺序很重要,你可以使用列表推导式来实现:
>>> [i for i, j in zip(a, b) if i == j]
[5]
(仅适用于相同大小的列表,因为顺序的重要性意味着这一点)。
&
)或者set(a).intersection(b)
可能会和列表推导式一样快或者更快。 - Joshmakerset(a) & set(b)
的时间复杂度是什么? - AdjunctProfessorFalconbool(set(a).intersection(b))
的意思是判断集合a和b是否有交集,如果有返回True,否则返回False。 - Akshaydifference
或union
方法。这两个方法的详细说明可以在Python官方文档的frozenset.difference和frozenset.union中找到。 - Shihe Zhang.intersection()
和&
之间有性能差异吗? - brandonbanks快速性能测试表明Lutz的解决方案是最好的:
import time
def speed_test(func):
def wrapper(*args, **kwargs):
t1 = time.time()
for x in xrange(5000):
results = func(*args, **kwargs)
t2 = time.time()
print '%s took %0.3f ms' % (func.func_name, (t2-t1)*1000.0)
return results
return wrapper
@speed_test
def compare_bitwise(x, y):
set_x = frozenset(x)
set_y = frozenset(y)
return set_x & set_y
@speed_test
def compare_listcomp(x, y):
return [i for i, j in zip(x, y) if i == j]
@speed_test
def compare_intersect(x, y):
return frozenset(x).intersection(y)
# Comparing short lists
a = [1, 2, 3, 4, 5]
b = [9, 8, 7, 6, 5]
compare_bitwise(a, b)
compare_listcomp(a, b)
compare_intersect(a, b)
# Comparing longer lists
import random
a = random.sample(xrange(100000), 10000)
b = random.sample(xrange(100000), 10000)
compare_bitwise(a, b)
compare_listcomp(a, b)
compare_intersect(a, b)
这是在我的电脑上得到的结果:
# Short list:
compare_bitwise took 10.145 ms
compare_listcomp took 11.157 ms
compare_intersect took 7.461 ms
# Long list:
compare_bitwise took 11203.709 ms
compare_listcomp took 17361.736 ms
compare_intersect took 6833.768 ms
显然,任何人为的性能测试都应该持保留态度,但由于set().intersection()
的答案至少和其他解决方案一样快,并且也是最易读的,它应该成为这个常见问题的标准解决方案。
list
创建一个新的set
不会从原始的list
中删除任何内容。如果您想要处理列表中的重复项的特殊逻辑,我认为您需要提出一个新问题,因为答案将需要根据您希望如何处理重复项而具体指定。 - Joshmaker我更喜欢基于集合的答案,但这里有一个仍然可以工作的答案。
[x for x in a if x in b]
一种快速的方法:
list(set(a).intersection(set(b)))
最简单的方法是使用集合:
>>> a = [1, 2, 3, 4, 5]
>>> b = [9, 8, 7, 6, 5]
>>> set(a) & set(b)
set([5])
你也可以尝试这个方法,将共同的元素保留在一个新列表中。
new_list = []
for element in a:
if element in b:
new_list.append(element)
>>> s = ['a','b','c']
>>> f = ['a','b','d','c']
>>> ss= set(s)
>>> fs =set(f)
>>> print ss.intersection(fs)
**set(['a', 'c', 'b'])**
>>> print ss.union(fs)
**set(['a', 'c', 'b', 'd'])**
>>> print ss.union(fs) - ss.intersection(fs)
**set(['d'])**
你需要重复吗?如果不需要,也许你应该使用集合:
>>> set([1, 2, 3, 4, 5]).intersection(set([9, 8, 7, 6, 5]))
set([5])
- Timothy Pratleyintersect([1, 2, 3, 4, 5], [9, 8, 7, 6, 5]) [5]
检查列表1(lst1)和列表2(lst2)的相等性的另一种更加功能性的方法,其中对象深度为1,并且保持顺序的方法是:
all(i == j for i, j in zip(lst1, lst2))