2011-08-21 21 views
10

Sto provando Java 7 ThreadLocalRandom e vedo che sta generando esattamente gli stessi numeri casuali su più thread.Java 7: ThreadLocalRandom che genera gli stessi numeri casuali

Ecco il mio codice, in cui creo 5 fili e stampati da ogni filo su 5 numeri casuali:

//5 threads 
for(int i = 0; i < 5 ; i++) { 
    final Thread thread = new Thread() { 
     @Override 
     public void run() { 
      System.out.print(Thread.currentThread().getName()+":"); 

      //each thread prints 5 random numbers 
      for(int j = 0 ; j < 5; j++) { 
       final int random = ThreadLocalRandom.current().nextInt(1,100); 
       System.out.print(random + ","); 
      } 
      System.out.println(); 
     } 
    }; 
    thread.start(); 
    thread.join(); 
} 

uscita:

Thread-0:1,93,45,75,29, 
Thread-1:1,93,45,75,29, 
Thread-2:1,93,45,75,29, 
Thread-3:1,93,45,75,29, 
Thread-4:1,93,45,75,29, 

Perche 'si ottengono gli stessi numeri casuali per ogni thread e per ogni esecuzione del programma?

risposta

10

Sembra che ci sia un bug aperto su questo problema. Vedere here e here

+0

+1 Nifty things bugs – Matt

+2

Il bug è stato risolto nell'aggiornamento 2 di JDK7. Scarica qui: http://www.oracle.com/technetwork/java/javase/downloads/jdk-7u2-download-1377129.html – jopasserat

1

Non è questo il motivo per cui i fili vengono creati all'incirca nello stesso tempo e quindi vengono seminati lo stesso valore dal timer? Avevo l'impressione che fosse così che funzionava, anche se potrei sbagliarmi.

+0

Non è lo stesso tempo, v'è un grande differenza di orario: ogni thread viene creato solo dopo la chiusura del thread precedente. – MByD

5

googling per la "fonte ThreadLocalRandom" mi ha dato http://www.assembla.com/code/scala-eclipse-toolchain/git/nodes/src/forkjoin/scala/concurrent/forkjoin/ThreadLocalRandom.java

long/short di esso: si usa un ThreadLocal<ThreadLocalRandom> che chiama la no-arg di costruzione per la costruzione

che costruttore no-arg è

/** 
* Constructor called only by localRandom.initialValue. 
* We rely on the fact that the superclass no-arg constructor 
* invokes setSeed exactly once to initialize. 
*/ 
ThreadLocalRandom() { 
    super(); 
} 

il super no-arg in Random chiamate questo (lungo) con un seme unico

, tuttavia, che il costruttore fa

public Random(long seed) { 
    this.seed = new AtomicLong(initialScramble(seed)); 
} 

cioè non il comportamento previsto dalla documentazione

e ThreadLocalRandom non/non può utilizzare il privato seed

+1

Questa non è la fonte JDK (notare i suggerimenti 'eclipse' e' scala' in l'URL). La vera sorgente JDK è su http://hg.openjdk.java.net, e qui ['ThreadLocalRandom'] (http://hg.openjdk.java.net/jdk8/jdk8/jdk/file/tip/src/ share/classes/java/util/concorrente/ThreadLocalRandom.java) – dimo414

Problemi correlati