力扣470
第一步:根据Rand7()函数制作一个可以随机等概率生成0和1的函数rand_0and1
调用Rand7()函数,随机等概率生成1,2,3,4,5,6,7
这时我们设置:生成1,2,3(也就是小于4)的时候,我们的rand_0and1函数就返回0
生成4,5,6(也就是小于4)的时候,我们的rand_0and1函数就返回1
如果生成7,那我们继续再调用一次Rand7()函数
public int rand_0and1()
{
int temp=rand7();
int result=0;
if(temp<4)
{
result=0;
}
else if(result>=4&&result<7)
{
result=1;
}
else//temp=7
{
while(temp!=7)
{
temp=rand7();
}
//跳出循环说明终于得到一个不为7的随机数,1,2,3,4,5,6其中之一
result=temp<4?0:1;
}
reurn result;
}
第二步:要生成的是1~10,我们先生成0~9(然后加1即可),怎么由我们第一步得到的0~1生成0~9呢?
1个二进制位可以保证等概率返回0,1
2个二进制位可以保证等概率返回0,1,2,3
3个二进制位可以保证等概率返回0,1,2,3,4,5,6,7
4个二进制位就可以保证等概率返回(最小是0000,最大是1111十五)0,1,2,3,4,5,6,7.......15
当发现返回的大于9,那就重新生成一个新的数,直到生成一个0~9之间的数
记rand_0and1()产生的值为temp
class Solution extends SolBase
{
public int rand10()
{
int result=0;
result=(rand_0and1())+(rand_0and1()<<1)+(rand_0and1()<<2)+(rand_0and1()<<3);
if(result<10)
{
return result+1;
}
else
{
while(result>=10)
{
result=(rand_0and1())+(rand_0and1()<<1)+(rand_0and1()<<2)+(rand_0and1()<<3);
}
//跳出循环,说明终于生成了一个比10小的数,符合要求
return result+1;
}
}
public int rand_0and1()
{
int result=0;
result=rand7();
if(result<4)
{
return 0;
}
else if(result>=4&&result<7)
{
return 1;
}
else//result=7
{
while(result==7)
{
result=rand7();
}
//跳出循环说明终于得到一个不为7的随机数
return result<4?0:1;
}
}
}
通过rand5()生成rand7()也是一样的,
第一步:先通过rand5()函数制作一个可以随机等概率生成0和1的函数rand_0and1(生成1,2就返回0,生成3,4就返回1,生成5就重新再生成1个数,直到生成不等于5的数返回0或者1)
第二步:通过rand_0and1随机等概率生成0~6
result=(rand_0and1())+(rand_0and1()<<1)+(rand_0and1()<<2);
生成大于6的数,就重新生成,直到生成一个小于等于6的数