Java的随机数原理
Java生成随机数时,可以会使用以下方法
final int i = new Random().nextInt(int bound);
或者
final double v = Math.random();
初一看,以为是两种方式,其实第二种的底层也是使用了Random
的方法nextDouble()
,所以我们主要看Random
的方法即可。
原理
计算机生成随机数,有几种方式
1.物理方式
正在意义上的随机数生成器,无法预测且无周期,一般利用计算机的电阻、热噪声等得到随机数,不过物理方式生成随机数的效率不高,需要计算机高效的计算。
2.随机数表方式
事先生成好随机数,放在内存里,需要时从表里获取,这种需要内存,如果随机数量非常大,那将需要很大的内存。
3.伪随机数方式
使用“种子”来生成随机数序列,使用算法在种子基础上生成随机数,由于是算法生成的,伪随机数生成是可以预测且周期性的,并不算是真正意义上的随机,所以叫伪随机数。
同余法
同余公式(congruential formula)是一种常用的伪随机数算法。在Java中,线性同余算法就是同余算法的一种变种。Random类中,使用了48(bit)位作为种子,在线性同余算法中生成随机数。
使得结果小于某个数,一般使用取余的计算,结果都是同一除数的余数,所以叫做同余法。
nextInt(int bound)方法会返回一个伪随机的,均匀分布于0(包含)到bound(不包含)之间的int值。
public int nextInt(int bound) {if (bound <= 0)throw new IllegalArgumentException(BadBound);int r = next(31);int m = bound - 1;if ((bound & m) == 0) // i.e., bound is a power of 2r = (int)((bound * (long)r) >> 31);else {for (int u = r;u - (r = u % bound) + m < 0;u = next(31));}return r;}
其中next(int bit)
方法源码
protected int next(int bits) {long oldseed, nextseed;AtomicLong seed = this.seed;do {oldseed = seed.get();nextseed = (oldseed * multiplier + addend) & mask;} while (!seed.compareAndSet(oldseed, nextseed));return (int)(nextseed >>> (48 - bits));}
线性同余公式就是这一行代码,
nextseed = (oldseed * multiplier + addend) & mask;
这个和以下线性公式非常相似
Xn+1=(a*Xn+c)(mod m)
Xn刚开始时就是初始化时的“种子”,经过运算会得到新的“种子”nextseed作为下一次运算的“种子”oldseed。
或许,你觉得疑惑求余,没看到有取余的计算,可以看看multiplier
,addend
,mask
变量
private static final long multiplier = 0x5DEECE66DL;private static final long addend = 0xBL;private static final long mask = (1L << 48) - 1;
和mask(即是 (1L << 48) - 1)作与运算,就是取余的运算。
Java的随机数原理相关推荐
- Java生成随机数原理_Java中随机数的产生方式与原理详解
Java中随机数的产生方式与原理 查阅随机数相关资料,特做整理 首先说一下java中产生随机数的几种方式 在j2se中我们可以使用Math.random()方法来产生一个随机数,这个产生的随机数是0- ...
- Java中随机数的原理,以及使用时的注意点
转载自 Java中随机数的原理,以及使用时的注意点 1 前言 一提到 Java 中的随机数,很多人就会想到 Random,当出现生成随机数这样需求时,大多数人都会选择使用 Random 来生成随机 ...
- Java篇 - 随机数的原理、伪随机和优化
这篇来说说Java中的随机数,以及为什么说随机数是伪随机. 目录: Math.random() Random类 伪随机 如何优化随机 封装的一个随机处理工具类 1. Math.random() 1.1 ...
- Java获得随机数的几种方法
转自http://blog.sina.com.cn/s/blog_4f925fc30100uvur.html 方法1 (数据类型)(最小值+Math.random()*(最大值-最小值+1)) 例: ...
- Java获取随机数的3种方法和总结
方法1 (数据类型)(最小值+Math.random()*(最大值-最小值+1)) 例: (int)(1+Math.random()*(10-1+1)) 从1到10的int型随数 方法2 获得随机数 ...
- java获取随机数方法_JAVA获取随机数
原文链接: http://blog.csdn.net/herrapfel/article/details/1885016 在Java中我们可以使用java.util.Random类来产生一个随机数发生 ...
- java获取随机数方法_《Java语言程序设计》Java获取随机数方法
<Java语言程序设计>Java获取随机数方法 在Java中我们可以使用java.util.Random类来产生一个随机数发生器.它有两种形式的构造函数,分别是Random()和Rando ...
- java lock的原理,Java中Lock原理探究
在对于lock锁的使用上,很多人只是掌握了最基础的方法,但是对实现的过程不是很清楚.这里我们对lock锁功能的实现进行分析,以ReentrantLock为例,分析它的锁类型,并对相关的调用方法进行展示 ...
- Java并发编程原理与实战六:主线程等待子线程解决方案
Java并发编程原理与实战六:主线程等待子线程解决方案 参考文章: (1)Java并发编程原理与实战六:主线程等待子线程解决方案 (2)https://www.cnblogs.com/pony1223 ...
- Java虚拟机工作原理详解
原文地址:http://blog.csdn.net/bingduanlbd/article/details/8363734 一.类加载器 首先来看一下java程序的执行过程. 从这个框图很容易大体上了 ...
最新文章
- 对话英特尔研究院院长:量子计算是马拉松,现在大家(包括谷歌)刚跑出第一英里...
- 皮一皮:好一道举世佳酿“青山卧雪龙”...
- 洛谷 P1101 单词方阵
- 【转】王晟教授:给光纤3室研究生的一封公开信
- 利用Selenium爬取淘宝商品信息
- PHP API接口签名验证
- Web前端技术历经的洗礼和蜕变
- 最长递增子序列和网易去除最少使从左向右递增又递减问题
- oracle修改字符集
- P2181 对角线(python3实现)
- FFmpeg--命令详解
- java扩展数组_Java数组扩展
- oracle存储过程数量,Oracle:存储过程的可变参数数量
- 大数据分析平台的作用有什么
- Python模块02/序列化/os模块/sys模块/haslib加密/collections
- 10部顶级数学纪录片
- 【CGAL】编译(windos)
- Yate for Mac音乐标签管理工具
- Auto.js学习笔记13:images.findImag()报错找不到方法,返回的坐标无法点击等问题利用图片的相似度执行精准目标点击(实战篇)
- apple pay 技术_如何在Apple Watch上设置和使用Apple Pay