如何有效地随机化所有相同浮点数的相对较小的数组,保留总和?

时间:2013-04-19 02:20:26

标签: javascript math

如何有效地随机化所有相同浮点数的相对较小的数组,保留总和?

例如:

我有一组相等的浮点数:

[ 0.1, 0.1, 0.1, 0.1, 0.1 ] // sum === 0.5

我想将它随机化:

[ 0.1, 0.2, 0.0, 0.15, 0.05 ] // sum === 0.5

初始数组总是具有相同的值,但它可以在各种范围内:

[ 3.56, 3.56, 3.56, 3.56, 3.56 ]

我不知道这些初始阵列的最终实际大小,但我猜它们的长度在50到100之间。

(仅供参考:这些是音符持续时间,如果算法是音乐会的奖励积分)

2 个答案:

答案 0 :(得分:6)

1)计算0和1之间的n个随机浮点数

2)计算这n个数的总和。

3)你必须将总和除以自己,然后乘以你想得的总和(在下面的结果中)。因此,如果将1)中生成的n个数中的每一个除以2)中计算的总和,并将结果与​​结果相乘,则得到结果中所需的随机数。

答案 1 :(得分:2)

不是音乐剧,但是:

1)计算数组中所有值的总和。

2)在0和sum之间生成N-1个点,其中N是数组中的条目数。

3)将这些N-1个点从最小到最大排序,然后在左边增加0,在右边增加和。基本上,想象一下你已经采用sum长度的条形并将其切成N-1点。

4)对于现在N + 1个点(不包括第一个)中的每个元素,计算它与前一个点之间的差异。这些差异的总和仍为sum - 您可以通过想象切碎的条形图的差异来证明这一点。如果你将长度为1的条形切割为0.2和0.7,则增加到0,0.2,0.7,1.0,差值为0.2,0.5,0.3,总和为1.

5)随机播放4)的输出(Fisher-Yates shuffle如果你需要实现它)


如果你想把它变成音乐剧,你可能想要“斟酌”第2步,我的意思是:

a)将数组的第一个元素除以2(称为D)(例如0.1 / 2 = 0.05)

b)将和除以D(称为Sd)(例如0.5 / 0.05 = 10)

c)创建从0到Sd的随机数作为整数,然后将它们乘以D

d)现在从原始算法中的3继续

这只会给你半定时器。如果您使用4而不是2,则会获得semidemiquavers,依此类推