5

如果我需要将例如 7 分成随机数量的随机大小的元素,我该怎么做?

所以有时我会得到 [3,4],有时会得到 [2,3,1],有时会得到 [2,2,1,1,0,1]?

我想这很简单,但我似乎无法得到结果。这是我试图在代码方面做的事情(不起作用):

def split_big_num(num):
    partition = randint(1,int(4))
    piece = randint(1,int(num))
    result = []
    for i in range(partition):
        element = num-piece
        result.append(element)
        piece = randint(0,element)
#What's next?
        if num - piece == 0:
            return result
    return result

编辑:每个结果数字都应该小于初始数字,并且零的数量应该不小于分区的数量。

4

4 回答 4

14

我会去下一个:

>>> def decomposition(i):
        while i > 0:
            n = random.randint(1, i)
            yield n
            i -= n

>>> list(decomposition(7))
[2, 4, 1]
>>> list(decomposition(7))
[2, 1, 3, 1]
>>> list(decomposition(7))
[3, 1, 3]
>>> list(decomposition(7))
[6, 1]
>>> list(decomposition(7))
[5, 1, 1]

但是,我不确定这种随机分布是否完全均匀。

于 2012-04-24T20:19:03.277 回答
4

您必须定义“随机”的含义。如果你想要一个任意整数分区,你可以生成所有整数分区,并使用random.choice. 请参阅python:生成整数分区这将不会给出 0 的结果。如果您允许 0,则您将不得不允许具有可能无限数量的 0 的结果。

或者,如果您只想删除随机块,请执行以下操作:

def arbitraryPartitionLessThan(n):
    """Returns an arbitrary non-random partition where no number is >=n"""
    while n>0:
        x = random.randrange(1,n) if n!=1 else 1
        yield x
        n -= x

由于每个数字应该小于原始数字的问题约束,有点尴尬;如果您允许原始数字,它会更优雅。如果您想要 0,您可以执行 randrange(n) ,但除非有隐藏的原因您不共享,否则它没有意义。

针对问题编辑进行编辑:由于您希望“零的数量不应少于分区的数量”,因此您可以在末尾任意添加 0:

def potentiallyInfiniteCopies(x):
    while random.random()<0.5:
        yield x

x = list(arbitraryPartitionLessThan(n))
x += [0]*len(x) + list(potentiallyInfiniteCopies(0))

这个问题非常随意,我强烈建议您选择这个作为您的答案:

def arbitraryPartition(n):
    """Returns an arbitrary non-random partition"""
    while n>0:
        x = random.randrange(1,n+1)
        yield x
        n -= x
于 2012-04-24T20:15:09.130 回答
2

递归救援:

import random

def splitnum(num, lst=[]):
    if num == 0:
        return lst
    n = random.randint(0, num)
    return splitnum(num - n, lst + [n])

for i in range(10):
    print splitnum(7)

结果:

[1, 6]
[6, 0, 0, 1]
[5, 1, 1]
[6, 0, 1]
[2, 0, 3, 1, 1]
[7]
[2, 1, 0, 4]
[7]
[3, 4]
[2, 0, 4, 1]
于 2012-04-24T20:20:02.810 回答
0

此解决方案不插入 0(我不明白您对零规则的描述应该是什么),并且同样可能生成除原始数字之外的所有可能组合。

def split (n):
    answer = [1]
    for i in range(n - 1):
        if random.random() < 0.5:
            answer[-1] += 1
        else:
            answer.append(1)

    if answer == [n]:
        return split(n)
    else:
        return answer
于 2012-04-24T22:02:23.397 回答