随机数 C语言

怎样获得某一范围的随机整数?

直接使用这种方法:
  rand()%N;
(试图返回从0到N-1的整数)不好,因为许多随机数生成器的低位并不随机。
 一个较好的方法是:
   (int)((double)rand()/((double)RAND_MAX+1)*N)
两种方法都需要知道RAND_MAX,而且假设N要远远小于RAND_MAX。

 如果N值接近RAND_MAX而随机数生成器的范围又不是N的整数倍(即(RAND_MAX+1)%N!=0),则这些方法都会失效,某些输出会比其他的频率更高。(使用浮点数也没有帮助。问题在于rand返回RAND_MAX+1个互不相同的值,这些值不一定总是能被均分N块。)如果出现这种问题,大概唯一能做的就是多次调用rand函数,然后丢弃某些值:
  unsigned int x=(RAND_MAX+1u)/N;
  unsigned int y=x*N;
  unsigned int r;
  do{
   r=rand();
}while(r>=y)
return r/x;

在这种技术中,在需要的时候改变生成随机数的范围都很简单,用下边的方式可以生成{M,N}范围的随机整数:
  M+rand()/(RAND_MAX/(N-M+1)+1)
(随便提一下,RAND_MAX是一个常数,他告诉你C语言库函数rand的固定范围,不能将RAND_MAX设为其他值,也不能要求rand返回其他范围的值。)

如果你用的随机数生成器返回的是0到1的浮点数,要取得范围0到N-1的整数,只要将随机数乘以N就可以了:
  (int)(drand()*N)

每次执行程序,rand都返回相同的数字序列。为什么?

  这是多数伪随机数生成器的一个特征(也是C语言库函数的定义特征),他们生成的随机数总是从同一个数字开始,然后是同一个序列。(除了别的考量,增加一点可预测性会让调试变得容易。)如果不需要这种可预测性,可以调用srand用真正随机数的值来初始化模拟随机数生成的种子。常见的种子值可以是当前时间或用用户案件之前过去的时间(当然很难可移植的判断按键时间)。这里有个使用当前时间的例子:
  #include
  #include
  srand((unsigned int)time(time_t*)NULL);
  但是,这个代码并不完美---其中,time()返回的time_t可能是浮点值,转换到无符号整数是可能上溢,这造成不可移植。

  还要注意到,在一个程序执行中多次调用srand并不见得由帮助,特别是不要为了试图取得“真随机数”而在每次调用rang前都调用srand。

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值