第3章 Java并发包中的ThreadLocalRandom类原理剖析

    下面以nextInt(int bound) 方法为例来分析Random的源码

    由此可见,生成新的随机数需要两步:

    • 由新的种子计算出新的随机数

    但多线程下,不同线程可能拿着同一个老的种子去计算新种子,如果next方法因此返回相同的值的话,由于(*)处的算法是固定的,这会导致不同线程生成相同的随机数,这并非我们想要的。所以next方法使用CAS操作保证每次只有一个线程可以更新老的种子,失败的线程则重新获取,这样就解决了上述问题。

    但这样处理仍有一个缺陷:当多个线程同时计算随机数来计算新的种子时,多个线程会竞争同一个原子变量的更新操作,由于该操作为CAS操作,同时只有一个线程会成功,这样会造成大量的自旋重试,导致并发性能降低。而ThreadLocalRandom可以完美解决此问题。

    如果线程中第一次调用current()方法,则调用localInit()进行初始化设置当前线程中的threadLocalRandomProb和threadLocalRandomSeed变量。

    下面来看int nextInt(int bound)方法

    相关笔记: