使用zip(),map()函数和itertools对列表中的列表元素求和

时间:2019-04-15 23:57:24

标签: python dictionary sum itertools

我正在编写一个程序,研究给定X面带有X面的骰子掷骰的每一个可能的总和。例如,对于2个骰子和6个面,我需要一个元素列表,给出这些骰子可实现的所有可能的唯一总和(例如2,3、3、4、4、4、4等)。我可以为较小的集合(2个骰子6个面都可以)执行此操作,但是较大的集合(如10个骰子和10个面)会遇到内存问题。我想我已经找到了解决方案,但是在实现方面遇到了问题。

我有一个列表列表,其中包含每个骰子的所有掷骰。对于此示例,我们有3个骰子可以掷出1、2或3。

dice = [[1,2,3], [1,2,3], [1,2,3]]

outcomes = list(map(sum, zip(itertools.product(*dice))))

我认为这些组件已经存在,但我不断收到TypeError:+不支持的操作数类型:“ int”和“ tuple”。我尝试过以多种方式移动这些片段,但是没有任何点击。我究竟做错了什么?最终,我得到一个数字,比如6,我必须找出将这个数字翻几率的几率。所以我上面的代码的目标是得到一个生成器,让我得到出现X数的总次数,并弄清楚滚动X数的可能性。我已经有了一个较小输入的列表,但是就像我说的那样,一旦获得较大输入,列表就会变得太大

2 个答案:

答案 0 :(得分:0)

您在这里不需要zip。直接将itertools.product生成的元组序列映射到sum,这将是您要寻找的和序列:

outcomes = list(map(sum, itertools.product(*dice)))

答案 1 :(得分:0)

对于任何给定的骰子集,您都知道骰子掷骰的最小总和为min_value * num_dice。例如,如果您有2个骰子和6个面,则最小骰子总和值为1 * 2 = 2。同样,您知道最大值将为max_value * num_dice。例如,如果您有2个骰子和6个面,则最大骰子总和值为6 * 2 = 12

此外,如果我们可以假设骰子都具有相同的值,并且每个面都具有唯一的数字并且数字在[1, number_of_sides]的范围内,则min_valuemax_value将被考虑。

因此,在python中,您可以简单地列出n边与x边的所有唯一和,如下所示:

def all_possible_sums(number_of_dice: int, number_of_sides: int) -> List[int]:
    return list(range(number_of_dice, number_of_sides * number_of_dice + 1))