我想把10
分成4个随机数的数组,但不能是0
或大于4
。例如[1,2,3,4]
,[1,4,4,1]
或[4,2,3,1]
。
我想这是一个简单的问题,但由于某种原因,我想不出如何做到这一点。如果有人有一些指导,这将是非常有帮助的!
编辑:这是我现在的代码,但我也生成了一个总数在10以下的代码:
let formation = [];
let total = 0;
for (let i = 0; i < 4; i ++) {
if (total < 9) {
formation[i] = Math.floor(Math.random() * 4) + 1;
} else {
formation[i] = 1;
}
}
字符串
9条答案
按热度按时间mftmpeh81#
你可以创建所有可能的组合,然后选择一个随机数组。
个字符
一种不需要所有可能组合列表就能获取随机值的算法
它的工作原理是使用一个随机值的因子和一个偏移量,基于实际和,索引,下一个索引所需的最小和,以及最大和。
偏移量通常是最小和,或者是和与最大和之差的较大值。为了获得因子,取三个值作为最小值,用于乘以随机值。
该表根据给定值和获取所有值的迭代,说明了总和的所有可能值和所需的迭代。
在开始时,和是用于小部分分布的值。结果是第二个块的剩余和为
14
...10
,因为可以取1
...5
的值。第三轮遵循相同的规则。在结束时,剩余的和被用作值的偏移。一个
1
,.,5
值和5
元素的例子,其总和为15
和所有可能性:型
示例代码采用目标
1
,...,4
,长度为4
部分,总和为10
。13z8s7eq2#
有点晚了,但我发现这是一个有趣的任务,所以在这里你去思考。我的方法不需要创建所有分区,它也不依赖于纯粹的运气找到一个随机匹配,它是紧凑的,它应该是公正的。
即使在使用大值时,只要
max
没有太大的限制,它也能有效地工作。字符串
dtcbnfnu3#
最简单的解决办法就是暴力破解。
1.创建一个
while
循环来嵌套计算1.在循环中,创建一个空数组,并使用随机值填充它,直到达到长度
1.检查数组的和是否是您想要的值,如果是,则中断循环
上面的应该运行,直到你有一个结果。
但有两件事值得考虑。
1.你可以很容易地测试一个解决方案是否可行,通过计算,length-of-array times minimum-value 不大于和,length-of-array times maximum-value 不小于和。
1.基于随机条件的循环可能永远运行,因此最大迭代量可能是可取的。
这两点都在下面的片段中考虑:
字符串
编辑1 -大计算
使用requestAnimationFrame和Promises,代码现在可以异步执行,这允许更长的计算时间,而不会打扰用户。
我还使
random
函数与剩余的范围成比例,大大减少了大数字所需的计算量。6kkfgxo04#
基本上,您需要
10
的分区(参见https://en.wikipedia.org/wiki/Partition_(number_theory)),并在结果集上应用您的条件。字符串
8dtrkrch5#
鉴于:
在一个n个正数的集合中,它们的总和为S,其中至少有一个将小于S除以n(S/n)
并且你想要一个结果集正好是4个数字,
你可以使用以下算法:
1.从范围[1,floor(S/n)]中获取一个随机数,在这种情况下floor(10/4)= 2,因此在范围[1,2]中获取一个随机数。让我们将其标记为x1。
1.从范围[1,floor((S - x1)/(n - 1))]中获取一个随机数。让我们将其标记为x2。
1.从范围[1,floor((S-x1- x2)/(n - 2))]中获取一个随机数。
1.继续,直到得到x(n-1)。
1.通过执行S-x1- x2.... - x(n-1)得到最后一个数字。
最后,对上述算法进行扩展,增加一个限制随机数上限的条件。
在n步骤,你可以得到一个集合。
字符串
参考
My answer using the same algorithm for another question的
zazmityj6#
快速、简单,但有偏见和非确定性终止
个字符
while循环可以无限小的概率永远循环。为了防止这种情况,你可以保留另一个“有效索引”数组,并在值达到max时删除其中的键。
3lxsmp7m7#
我只是一个偶然发现这一页的中学数学老师,但我想知道这是否是一个好的解决方案:
字符串
hzbexzde8#
这将计算从1到4的随机数
根据需要将其 Package 在函数中以生成数组
字符串
型
kognpnkq9#
太简单了。
字符串