我想生成 9 个非零随机数,其总和为 250。 我试过下面的代码,它给了我 9 个随机数,但有些数字是零。
public void n_random()
{
Random r = new Random();
ArrayList<Integer> load = new ArrayList<Integer>();
int temp = 0;
int sum = 0;
for (int i = 1; i <= 9; i++) {
if (!(i == 9)) {
temp = r.nextInt(250 - sum);
System.out.println("Temp " + (i) + " " + temp);
load.add(temp);
sum += temp;
} else {
int last = (250 - sum);
load.add(last);
sum += last;
}
}
System.out.println("Random arraylist " + load);
System.out.println("Sum is "+ sum);
}
我的错误在哪里或者我应该在哪里改进我的代码或任何其他解决方案?
最佳答案
我建议使用:
temp = r.nextInt((250 - sum) / (9 - i)) + 1;
这将确保:
- 每个数字都是正数
- 在达到第 9 个数字之前,您不会使用全部“250 津贴”
然而,结果的分布可能存在偏差。
示例输出:
Random arraylist [18, 28, 22, 19, 3, 53, 37, 49, 21]
解释:
(250 - sum)
是达到 250 的剩余数量,因此您不想超过它/(9 - i)
如果您的总和已达到例如 200(还需要 50)并且您还需要 5,请确保下一个随机数不超过 10,以为接下来的 4 次抽奖留出一些空间+1
防止0
另一种可能提供更好分布的替代方法是采用随机数并缩放它们以获得所需的总和。示例实现:
public static void n_random(int targetSum, int numberOfDraws) {
Random r = new Random();
List<Integer> load = new ArrayList<>();
//random numbers
int sum = 0;
for (int i = 0; i < numberOfDraws; i++) {
int next = r.nextInt(targetSum) + 1;
load.add(next);
sum += next;
}
//scale to the desired target sum
double scale = 1d * targetSum / sum;
sum = 0;
for (int i = 0; i < numberOfDraws; i++) {
load.set(i, (int) (load.get(i) * scale));
sum += load.get(i);
}
//take rounding issues into account
while(sum++ < targetSum) {
int i = r.nextInt(numberOfDraws);
load.set(i, load.get(i) + 1);
}
System.out.println("Random arraylist " + load);
System.out.println("Sum is "+ (sum - 1));
}
关于java - 生成n个随机数,其和为m且所有数都应大于零,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/22380890/