2012-11-23 58 views
4

我想模擬http://blog.xkcd.com/2010/02/09/math-puzzle/上找到的數學難題。然而,java隨機類正在返回奇怪的結果。在下面的代碼中,結果是預期的。第一行輸出約爲.612,第二行輸出在.49和.51之間。 int trials = 10000000; int success = 0;Java隨機類不是真正的隨機?

int returnstrue = 0; 

    for (int i = 0; i < trials; i++) { 
     Random r = new Random(); 
     //double one = r.nextDouble()*10000; 
     //double two = r.nextDouble()*10000; 
     double one = 1; 
     double two = Math.PI; 


     double check = r.nextDouble(); 
     boolean a = r.nextBoolean(); 


     if(a) 
     { 
      returnstrue++; 
     } 
     if(a){ 
      if((check>p(one)) && two > one) 
      { 
       success++; 
      } 
      if((check<p(one))&& two<one) 
      { 
       success++; 
      } 
     } 
     else{ 
      if((check>p(two)) && two < one) 
      { 
       success++; 
      } 
      if((check<p(two))&& two>one) 
      { 
       success++; 
      }  
     } 
    } 
    System.out.println(success/(double)trials); 
    System.out.println(returnstrue/(double)trials); 

然而,當我的

double check = r.nextDouble(); 
boolean a = r.nextBoolean(); 

線切換到

boolean a = r.nextBoolean(); 
    double check = r.nextDouble(); 

輸出是所述第一數量的第二週圍0.476和0.710。這意味着nextBoolean()方法在後面的配置中70%的時間返回true。我做錯了什麼或者這只是一個錯誤?

+0

@bmargulies我認爲它不夠可怕。但它絕對過於本地化。 –

+0

這只是另一個擁有太多「隨機」對象的人。 – bmargulies

+0

呃,那個提議的傻瓜根本就不是傻瓜!這個問題有一個完全不同的問題,因爲隨機數發生器根本不是在循環內部構建的。我全部是爲了解決重複的問題,但只有當他們是真實的而不是想象中的愚蠢時:-) – paxdiablo

回答

12

移動rfor循環的實例,如:

Random r = new Random(); 
for (int i = 0; i < trials; i++) { 
    : 
} 

你現在正在做的是創造一個新的每次循環迭代和時間,因爲種子是基於時間(毫秒),你可能會得到不少與相同的種子。

這幾乎可以肯定是什麼造成了結果的偏差。

所以,是的,它是一個錯誤,只是在代碼,而不是在Java中。當人們提出這個問題時,大約有99.9999%的情況是這種情況,因爲Java本身不斷被全球數百萬人測試,而且你的片段已經過測試,只有你:-)