【问题标题】:Cartesian product that returns outputs of varied lengths返回不同长度输出的笛卡尔积
【发布时间】:2015-05-06 09:33:55
【问题描述】:

所以我有这些列表:

a = [1, 2, 3]
b = [11, 12, 13, 14]
c = [21, 22, 23, 24, 25, 26]

我想获取所有可能的组合(重复即可),其中包含来自 a 的 2 个元素、来自 b 的 3 个元素和来自 c 的 3 个元素。像这样:

([1, 2], [11, 12, 13], [21, 22, 23]) # 1
([1, 2], [11, 12, 13], [22, 23, 24]) # 2
# all the way to...
([2, 3], [12, 13, 14], [24, 25, 26]) # 16

如果我使用itertools.product(),它只会给我每个列表中的 1 个:

import itertools

def cartesian(the_list):
    for i in itertools.product(*the_list):
        yield i

a = [1, 2, 3]
b = [11, 12, 13, 14]
c = [21, 22, 23, 24, 25, 26]

test = cartesian([a, b, c])

print(next(test)) 
# Gives (1, 11, 21). But I need ([1, 2], [11, 12, 13], [21, 22, 23])

print(next(test)) 
# Gives (1, 11, 22). But I need ([1, 2], [11, 12, 13], [22, 23, 24])

我可以使用多个嵌套的for 循环,但如果我有很多列表,我将需要太多循环。

那么我该如何实现一个算法,它可以给我所有可能的组合,每个组合都由每个输入列表中的一定数量的元素组成?

【问题讨论】:

    标签: python list python-3.x itertools cartesian-product


    【解决方案1】:

    构建一个生成器函数,它可以产生任意数量的值,并在product 中使用它,就像这样

    >>> from itertools import product
    >>> def get_chunks(items, number=3):
    ...     for i in range(len(items) - number + 1): 
    ...         yield items[i: i + number]
    ...     
    ... 
    

    然后定义你的cartesian 生成器,像这样

    >>> def cartesian(a, b, c):
    ...     for items in product(get_chunks(a, 2), get_chunks(b), get_chunks(c)):
    ...         yield items
    ...     
    ... 
    

    如果你使用的是 Python 3.3+,你实际上可以在这里使用yield from,像这样

    >>> def cartesian(a, b, c):
    ...     yield from product(get_chunks(a, 2), get_chunks(b), get_chunks(c))
    ... 
    

    然后,当您将所有元素作为列表获取时,您将得到

    >>> from pprint import pprint
    >>> pprint(list(cartesian([1, 2, 3],[11, 12, 13, 14],[21, 22, 23, 24, 25, 26])))
    [([1, 2], [11, 12, 13], [21, 22, 23]),
     ([1, 2], [11, 12, 13], [22, 23, 24]),
     ([1, 2], [11, 12, 13], [23, 24, 25]),
     ([1, 2], [11, 12, 13], [24, 25, 26]),
     ([1, 2], [12, 13, 14], [21, 22, 23]),
     ([1, 2], [12, 13, 14], [22, 23, 24]),
     ([1, 2], [12, 13, 14], [23, 24, 25]),
     ([1, 2], [12, 13, 14], [24, 25, 26]),
     ([2, 3], [11, 12, 13], [21, 22, 23]),
     ([2, 3], [11, 12, 13], [22, 23, 24]),
     ([2, 3], [11, 12, 13], [23, 24, 25]),
     ([2, 3], [11, 12, 13], [24, 25, 26]),
     ([2, 3], [12, 13, 14], [21, 22, 23]),
     ([2, 3], [12, 13, 14], [22, 23, 24]),
     ([2, 3], [12, 13, 14], [23, 24, 25]),
     ([2, 3], [12, 13, 14], [24, 25, 26])]
    

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 1970-01-01
      • 2014-04-08
      • 1970-01-01
      • 2018-12-26
      • 2017-12-14
      • 1970-01-01
      • 2017-06-29
      • 1970-01-01
      相关资源
      最近更新 更多