如,原来a,b,c,d,e都是20,随机后变成a=34b=29c=11d=10e=16,但是他们之和还是100,再次随机后a=11b=21c=13d=28e=27,他们的和还是100。
我的解决思路是,第一个数和第二个数在[10,35]中随机,后面的数随机要满足一定的条件:保证它之后的数随机后能在[10,35]之间,极端不满足的情况是前两个数都随机到35,那么后面的三个数只能都是10了,所以第三个数随机的时候要满足(100-a-b-c)/2>10||(100-a-b-c)/2<35,否则就要重新随机。第四个数跟第三个数的处理方式一样,第五个数是个用100减去前四个数就行。以下是我的实现:
public static void random(){ Random r = new Random(); int b,c,d,e; int a = r.nextInt(25)+10; b = r.nextInt(25)+10; c = r.nextInt(25)+10; while((100-a-b-c)/2<10||(100-a-b-c)/2>35){ c = r.nextInt(25)+10; } d = r.nextInt(25)+10; while((100-a-b-c-d)<10||(100-a-b-c-d)>35){ d = r.nextInt(25)+10; } e = 100-a-b-c-d; System.out.println("a="+a+"b="+b+"c="+c+"d="+d+"e="+e); }这里又想起一个有关随机的题目:给定一个函数rand5(),该函数可以随机生成1-5的整数,且生成概率一样。现要求使用该函数构造函数rand7(),使函数rand7()可以随机等概率的生成1-7的整数。
要保证rand7的等概率,就不能利用rand5() + rand()%3来实现rand7()函数,可以这样思考,首先构造一个1到n的等概率随机函数randn(),其中n>7,这样在randn函数内1-7之间的数肯定也是等概率的,把大于7的数丢弃就ok了。以下是我的代码:
//通过rand5随机1-7之间的数 public static int rand7(){ int t = rand5()+(rand5()-1)*5; while(t>22){ t = rand5()+(rand5()-1)*5; } return t%7+1;//这里把7的整数倍也用求余的方式映射到1-7. } //随机1-5之间的数 public static int rand5(){ Random r = new Random(); int i = r.nextInt(5)+1; return i; }这里又有一个更普遍的题目,通过randn()函数随机randm()函数,randn是等概率随机1-n之间的数,randm是等概率随机1-m之间的数。跟上面的思路一样,很容易写出代码:
//通过randn随机1-m之间的数。 public static int randm(int n,int m){ int t = n*n; int i=1; int max = (t/m)*m; int s = randn(n)+(randn(n)-1)*n; while(s>(max+1)){ s = randn(n)+(randn(n)-1)*n; } return s%m+1; } //随机1-n之间的数 public static int randn(int n){ Random r = new Random(); int i = r.nextInt(n)+1; return i; }