ThreadLocalRandom使用中出现相同结果
当我们在主线程中通过ThreadLocalRandom的current方法获得这个工具类的实例后,再在线程中使用这个实例的nextInt方法就会发现这些线程打印出来的结果是相同的。
public static voic main(String [] Args){`
ThreadLocalRandom rd=ThreadLocalRandom.current();
Thread thread1=new Thread(new Runnable() {
@Override
public void run() {
for(int i=0;i<5;i++) {
System.out.println(Thread.currentThread() + ":" + rd.nextInt(5));
}
}
});
Thread thread2=new Thread(new Runnable() {
@Override
public void run() {
for(int i=0;i<5;i++) {
System.out.println(Thread.currentThread() + ":" + rd.nextInt(5));
}
}
});
thread1.start();
thread2.start();`}
上面这段代码中线程1和线程2运行的结果是相同的。原因是因为这里只有主线程调用了ThreadLocalRandom的current方法,在这个方法中我们知道他会根据当前线程的一个属性是否为0来初始化当前线程用于计算随机数的种子。这里只有主线程调用了这个方法所以只有主线程的种子才会被初始化,而其他线程只是调用nextint方法,这个方法中有一个nextseed函数,这个函数就会获取当前线程的种子并修改种子。这些算法是相同的。线程1和2的种子都没被初始化所以就会出现相同的结果。
改进方案:
Thread thread1=new Thread(new Runnable() {
@Override
public void run() {
ThreadLocalRandom rd=ThreadLocalRandom.current();
for(int i=0;i<5;i++) {
System.out.println(Thread.currentThread() + ":" + rd.nextInt(5));
}
}
});
Thread thread2=new Thread(new Runnable() {
@Override
public void run() {
ThreadLocalRandom rd=ThreadLocalRandom.current();
for(int i=0;i<5;i++) {
System.out.println(Thread.currentThread() + ":" + rd.nextInt(5));
}
}
});
thread1.start();
thread2.start();`
每个线程都运行以下current方法。