【发布时间】:2014-09-27 00:51:10
【问题描述】:
假设我想递归地创建一个数字列表,方法是从 0 到 9 中随机选择一个数字开始,然后(可选)在 x+1 和 9 之间随机选择另一个数字,其中 x 是最后一个被选择的数字,选择性地重复这个过程。通过这种方式,您可以获得1,3,6、3,4,8,9、2,7 等列表。这是对我真正想做的事情的简化。
出于我的目的,我不想只是从列表中挑选一堆随机数,删除重复项,然后对它们进行排序。这需要递归地完成。问题是,以我描述的方式简单地做这件事不会给所有数字一个平等的机会。它倾向于选择较大的数字而不是较小的数字。我尝试了一些方法来抵消这一点,但它太偏爱小数字了。
这是使用 Lo-Dash 的随机整数函数的 javascript:
function randomlist(index) {
if (index > 8) return;
var range = _.random(9 - index);
var randex = [_.random(index, index + range)];
if (_.random(10) < 6) randex = randex.concat(randomlist(randex[0] + 1));
return randex
}
tally = [0,0,0,0,0,0,0,0,0,0]
for (i=0;i<1000;i++) {
var list = randomlist(0);
list.forEach(function(x){tally[x]+=1});
}
在这里,而不是仅仅在 x 和 9 之间选择一个随机数,然后首先选择一个随机的较小范围,然后在其中选择一个随机数。我认为它可以解决问题,但是当我运行上面的代码时,tally 最终看起来像[278, 262, 224, 189, 217, 180, 185, 179, 156, 61],显然更倾向于较小的数字。如果我调整递归的机会,那么平衡就会发生一些变化。我希望可能有一些公式允许可调整的递归机会并设法生成对所有数字进行均匀采样的列表。
【问题讨论】:
-
您是否错过了大数比小数多的事实,这就是为什么随机数函数倾向于更频繁地选择大数的原因?也许您应该将所有数字范围视为具有相同的位数——小的数字只是以 0 开头,例如 053 和 008。
-
为什么不选择数字之间的距离,然后通过扫描计算数字呢?通过扫描,我的意思是 [2,4,1,5,2] 变为 [2,6,7,12,14]。
-
你的概率分布是多少?您只想要前 10 个数字的均匀抽样随机子集吗?然后在每个递归步骤中,要么采用特定的项目,要么不采用。
-
@vernonner3voltazim,我不认为你理解我的问题,因为你的回答对我来说没有意义。
-
_.random(9 - index)索引等于 0 有相同的机会选择1或任何其他数字。但整体1出现的机会较少,因为它只能出现在第一个单元格中。因此,您应该将_.random(9 - index)替换为根据数组的最大大小赋予1更多权重的函数。您可以通过在Math 上询问来找到每个数字的确切权重。
标签: javascript recursion random-sample