Python列表与非唯一项目的交集

Ric*_*kyA 13 python intersection multiset

我有两个字符串,我想在它们上面有交集,包括重复的项目:

str_a = "aabbcc"
str_b = "aabd"

list(set(str_a) & set(str_b))
>> "ab"
Run Code Online (Sandbox Code Playgroud)

我想让它回归:

>> "aab"
Run Code Online (Sandbox Code Playgroud)

有任何想法吗?

nin*_*cko 18

Multisets在python 2.7或更高版本中实现为(可变)Counter对象.您可以对集合执行许多相同的操作,例如并集,交集,差异(尽管计数可以变为负数),等等:

from collections import Counter as mset
Run Code Online (Sandbox Code Playgroud)

解:

(mset("aabbcc") & mset("aabd")).elements()
Run Code Online (Sandbox Code Playgroud)

更多细节:

>>> intersection = mset("aabbcc") & mset("aabd")
Counter({'a': 2, 'b': 1})

>>> list(intersection.elements())
['a', 'a', 'b']

>>> ''.join(intersection.elements())
'aab'
Run Code Online (Sandbox Code Playgroud)

''.join如果你想要一个字符串,或者list()如果你想要一个列表,你可以使用,但我只是将其保持为可迭代格式intersection.elements().

  • @ninjagecko:不太好,你的`intersection`输出不正确,也很混乱. (2认同)
  • @ninjagecko:您的代码行`>>> intersection = ...`不会回显终端上的输出.你错过了一个明确的`>>>交叉点.而且,在你编辑`Counter([{..}])`输出之前,你的例子是不正确的.最后但并非最不重要的是,当我输入我的答案并在提示中测试时,你的答案仍然非常不正确.我可以向你保证,如果我们的答案看起来相似,那完全是巧合. (2认同)

Mar*_*ers 9

使用collections.Counter每个单词,并使用这些作为集:

>>> from collections import Counter
>>> str_a, str_b = 'aabbcc', 'aabd'
>>> Counter(str_a) & Counter(str_b)
Counter({'a': 2, 'b': 1})
>>> ''.join((Counter(str_a) & Counter(str_b)).elements())
'aab'
Run Code Online (Sandbox Code Playgroud)

它Counter是一个dict子类,但它会计算用它初始化它的序列的所有元素.因此,"aabbcc"成为Counter({'a': 2, 'b': 2, 'c': 2}).

计数器的行为类似于多重集合,因为当你在上面的交集中使用2时,它们的计数被设置为在任一计数器中找到的最小值,忽略计数下降到0的任何数据.如果你要计算它们的并集,最大计数将是改为使用.