提问人:alvas 提问时间:11/10/2023 最后编辑:alvas 更新时间:11/10/2023 访问量:55
可迭代对象差异和公共元素
Iterables difference and common elements
问:
给定 2 个可迭代对象/列表,目标是从两个列表中提取共同和不同的元素。
例如,给定:
x, y = [1,1,5,2,2,3,4,5,5], [2,3,4,5]
目标是实现:
common = [2,3,4,5]
x_only = [1,1,5,2,5]
y_only = []
解释:
- 当涉及到元素时,x 有 2 个计数,y 有 1 个计数,所以是共同的,另一个是x_only的。
2
[2]
[2]
- 类似地,x 有 3 个计数,y 有 1 个计数。所以会很常见,另一个会x_only。
5
[5]
[5,5]
- 和 中元素的顺序并不重要。
common
x_only
y_only
我试过:
from collections import Counter
x, y = [1,1,5,2,3,4,5], [2,3,4,5]
x_only = list((Counter(x) - Counter(y)).elements())
y_only = list((Counter(y) - Counter(x)).elements())
common = list((Counter(x) & Counter(y)).elements())
上述尝试达到了目标,但在重复多组/计数器减法和交集时似乎有点多余。它适用于小型可迭代对象,但不适用于大型列表,例如 1-100 亿个项目。
答:
3赞
ShadowRanger
11/10/2023
#1
你的解决方案很好,只需通过只构造每个唯一对象一次来消除冗余,首先进行交集,这样就可以减少组成唯一结果的工作量,这将使你能够完成大部分工作(所以只构造了三个对象,而不是九个):Counter
Counter
from collections import Counter
x, y = [1,1,5,2,3,4,5], [2,3,4,5]
cx = Counter(x)
cy = Counter(y)
both = cx & cy
cx -= both
cy -= both
x_only = list(cx.elements())
y_only = list(cy.elements())
common = list(both.elements())
它有更多的线条,但完成的工作更少,任何给定的线都远没有那么复杂。
评论
x
5
y
Counter