生成正态分布的数

java.util.Random里的nextGaussian(),生成的数值符合均值为0方差为1的高斯/正态分布,即符合标准正态分布。

产生数字的范围:任何数都有可能,不过在0左右的数字较多。

产生N(a,b)的数:Math.sqrt(b)*random.nextGaussian()+a

jdk实现:  (Math中地方法都是调用StrictMath来实现的)

 private double nextNextGaussian;
 private boolean haveNextNextGaussian = false;
 public double nextGaussian() {
  if (haveNextNextGaussian) {
  haveNextNextGaussian = false;
  return nextNextGaussian;
  } else {
  double v1, v2, s;
  do {
  v1 = 2 * nextDouble() - 1; // between -1.0 and 1.0
  v2 = 2 * nextDouble() - 1; // between -1.0 and 1.0
  s = v1 * v1 + v2 * v2;
  } while (s >= 1 || s == 0);
  double multiplier = StrictMath.sqrt(-2 * StrictMath.log(s)/s);
  nextNextGaussian = v2 * multiplier;
  haveNextNextGaussian = true;
  return v1 * multiplier;
  }
 }

 

独立同分布的中心极限定理:当样本量很大时,独立同分布的变量之和近似的服从正态分布.正态分布是一种自然分布,指的是大量的样本数据有趋近于一个特定的值的趋势,而且分布是均匀逼近的.

生成正态随机数的方法有很多,jdk中实现的方案具有较快的速度。

 

附:java随机数相关知识

http://lavasoft.blog.51cto.com/62575/113758/

http://blog.sina.com.cn/s/blog_4cbb6b0c0100080a.html

产生随机数需要一个基值seed,缺省为系统时间。用相同种子建立的Random对象返回的伪随机序列是相同的,即种子相同,依次产生出的数据是一样的。

计算机产生随机数不是真正的随机数,而是一种模拟随机数(伪随机数)。是通过输入一个种子数,然后通过对种子数进行计算产生一系列随机数,这些随机数是周期循环的。不同的算法有不同的循环周期。当然我们希望周期越长越好。相同的种子应该产生相同的随机数序列。这就是为什么我们需要用时间函数设种子数的原因,避免产生相同的随机数序列。纯粹的毫无规律的随机数用处不大。有用的是产生符合某种函数分布的随机数。例如最常用的是产生符合正态分布的随机数,因为在数值计算的时候,常常需要对随机事件进行模拟并求解,例如,计算银行窗口办理业务的效率问题,因为顾客来、排队、办理业务整个过程符合正态分布,因此计算效率问题就需要产生符合正态分布的随机数。

posted on 2012-05-28 12:40  山上明月  阅读(5447)  评论(1编辑  收藏  举报