生成n个随机数,它们的总和为m,所有数字均应大于零 [英] Generate n random numbers whose sum is m and all numbers should be greater than zero

查看:187
本文介绍了生成n个随机数,它们的总和为m,所有数字均应大于零的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我想生成9个非零随机数,其总和为250. 我尝试了以下代码,它给了我9个随机数,但有些数字为零.

I want to generate 9 non zero random numbers whose sum is 250. I have tried following code it gives me 9 random numbers but some numbers are zero.

 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);

}

我的错误在哪里,或者我应该在哪里改进我的代码或任何其他解决方案?

Where is my mistake or where i should improve my code or any other solution?

推荐答案

我建议使用:

temp = r.nextInt((250 - sum) / (9 - i)) + 1;

这将确保:

  • 每个数字都是严格的正数
  • 在达到第9个数字之前,您将不会使用全部的"250配额"

但是结果的分布可能有偏差.

However the distribution of the results is probably biased.

示例输出:

随机数组列表[18、28、22、19、3、53、37、49、21]

Random arraylist [18, 28, 22, 19, 3, 53, 37, 49, 21]

说明:

  • (250 - sum)是剩下的数量,可以达到250,所以您不想超过该数量
  • / (9 - i)如果您的总和达到例如200(需要再增加50),并且还有5个余数,请确保下一个随机数不超过10,以便在接下来的4次抽奖中留出一定的空间
  • + 1防止为0
  • (250 - sum) is the amount left to reach 250, so you don't want to go over that
  • / (9 - i) if your sum has reached for example 200 (need 50 more) and you have 5 more to go, make sure the next random number is not more than 10, to leave some room for the next 4 draws
  • + 1 to prevent 0

一个可能给出更好分布的替代方法是采用随机数并将其缩放以达到所需的总和.实施示例:

An alternative which probably gives a better distribution is to take random numbers and scale them to get to the desired sum. Example implementation:

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));
}

这篇关于生成n个随机数,它们的总和为m,所有数字均应大于零的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆