天天看點

Java中的随機數生成器:Random,ThreadLocalRandom,SecureRandom

文中的

random即:java.util.random,

threadlocalrandom 即:java.util.concurrent.threadlocalrandom

securerandom即:java.security.securerandom

q:random是不是線程安全的?

a:random是線程安全的,但是多線程下可能性能比較低。

參考:

http://docs.oracle.com/javase/7/docs/api/java/util/random.html

http://stackoverflow.com/questions/5819638/is-random-class-thread-safe

q:threadlocalrandom為什麼這麼快?

a:其實這個看下源碼就知道了。。因為random用了很多cas的類,threadlocalrandom根本沒有用到。

q:為什麼在高強度要求的情況下,不要用random?

a:特别是在生成驗證碼的情況下,不要使用random,因為它是線性可預測的。記得有個新聞說的是一個賭博網站,為了說明其公平,公開的它的源代碼,結果因為随機數可預測漏洞被攻擊了。是以在安全性要求比較高的場合,應當使用securerandom。

update 2014-4-22:  http://news.cnblogs.com/n/206074/

參考:http://www.inbreak.net/archives/349

q:從理論上來說計算機産生的随機數都是僞随機數,那麼如何産生高強度的随機數?

a:産生高強度的随機數,有兩個重要的因素:種子和算法。當然算法是可以有很多的,但是如何選擇種子是非常關鍵的因素。如random,它的種子是system.currenttimemillis(),是以它的随機數都是可預測的。那麼如何得到一個近似随機的種子?這裡有一個很别緻的思路:收集計算機的各種資訊,如鍵盤輸入時間,cpu時鐘,記憶體使用狀态,硬碟空閑空間,io延時,程序數量,線程數量等資訊,來得到一個近似随機的種子。這樣的話,除了理論上有破解的可能,實際上基本沒有被破解的可能。而事實上,現在的高強度的随機數生成器都是這樣實作的。

比如windows下的随機數生成器:

http://blogs.msdn.com/b/michael_howard/archive/2005/01/14/353379.aspx

http://msdn.microsoft.com/en-us/library/aa379942%28vs.85%29.aspx

linux下的 /dev/random:

http://zh.wikipedia.org/wiki//dev/random

據securerandom的java doc,說到在類unix系統下,有可能是利用 /dev/random,來實作的。

其它的一些有意思的東東:

最快的安全性要求不高的生成uuid的方法(注意,強度不高,有可能會重複):

在一個網站上看到的,忘記出處了。

随機生成産生随機數的函數?

是否可以利用一個随機數生成器來生成一系列的随機代碼,然後作為一個新的随機數生成器?貌似強度是傳遞的,似乎沒意義。