leetcode 470.用Rand7()实现Rand10()(拒绝采样+均匀随机整数详解)

刚开始看题目没有很好的理解题目的意思,后来仔细阅读题目,才发现题目中最重要的两个字是均匀

首先我们先考虑rand2()来完成rand4()

首先大家可能都会想到用相加的方法进行处理,构造出符号条件的结果。

rand2()+rand2():这样是完不成题目所要求的,        构造rand2()-1+rand2()

1+1=2                                                                                1-1+1=1

1+2=3                                                                                1-1+2=2

2+1=3                                                                                2-1+1=2

2+2=4                                                                                2-1+2=3  此构造出了rand3(),但不均匀

 (rand2()-1)*2+rand2()

(1-1)*2+1=1

(1-1)*2+2=2

(2-1)*2+1=3

(2-1)*2+2=4        构造出的结果完全满足要求,即为rand4(),每个值的概率也是均匀的。

经过多次举例,得到了下面这个公式,大家却不知下面这个公式对错与否,可先举例尝试。

(randX()-1)*Y+randY();        可得到在区间[1,X*Y]区间内的一个均匀整数。

OK,说完举例是这样的后,现在进一步说明原因,

以(rand7()-1)*7+rand7()为例证,

rand7()={1,2,3,4,5,6,7}

rand7()-1={0,1,2,3,4,5,6}

(rand7()-1)*7={0,7,14,21,28,35,42}

X和Y是两个相互不相关的部分,按照概率论的说法,这两者是相互不独立的。

 能得出[1,49]这个区间的所有数是符合均匀概率的。

从这引申到[1,X*Y]区间上必然每个数也是等概率的。

现在题目转换为:由rand49()怎么得出rand10()

明显看出49不是10的倍数,不能够均匀缩小到一个长度为10的区间上,保证每个整数的概率相等。

因此这里涉及到拒绝采样不懂的同学可以自己查资料看看

 我们构造了一个rand49(),那我们就可以取前40个概率相等的数字进行处理。

int num=(rand7()-1)*7+rand7();

while(num>40){
    num=(rand7()-1)*7+rand7();
}

 在这个过程中我们限制只取[1,40]区间的数,最后利用区间缩小办法,即1+(num-1)%10保证了区间的限制要求。

优化问题

 由于存在[41,49]的未命中区间,因此就需要尽可能的缩小未命中的区间,以达到优化的目的。

这样就能回答题目中的附加问,怎么尽可能减少调用rand7()的次数

 

 

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值