2017-02-07 2 views
-1

私はシミュレーションで乱数を作成するためにdev/urandomからループを読み込んでいました。それは動作していませんでした、私は最終的に次のコードサンプルに問題を追跡しましたdev/urandomから本当にランダムなデータを取得する

int myFile = open("/dev/urandom", O_RDONLY); 
begin outer loop 
for (ii = 0 ; ii<12 ; ii++) 
    { 
      read(myFile, &rand, 2) ; 
      printf("%d " , (int) rand) ; 
    } 

以下のような出力が得られます。これは明らかにランダムではありません。例えば54603という数字が36回連続して表示され、他のランでは数字が同様の回数連続して表示されます。 ここで何が起こっているのですか、私はdev/urandomからの読み込みはかなり乱数を与えるべきであるという印象を受けました。私はここで何か非常に間違っているのですか? FreeBSDの10.3とSolaris 11

14315 18369 22645 5910 55240 17092 32556 55028 34376 34902 44236 56796 
15767 54265 22372 38639 44446 25037 58094 28251 65329 48865 28057 59835 
17135 57009 5612 8627 55111 365 9988 62402 42682 57066 59920 10659 
21386 60845 9243 27377 18829 10162 64795 55836 53913 39765 51749 47917 
21522 30166 44059 30351 15622 17957 43399 26184 44558 4553 41745 54603 
2179 11970 21234 39538 45359 50854 58277 62479 4172 14207 20551 54455 
27120 22497 51021 41488 51668 50638 13894 37707 19813 40971 52191 27702 
29443 20239 59131 12186 24974 55298 56381 50092 11114 55533 11428 17223 
30520 32207 42256 31605 32485 3700 47741 25023 50723 64056 44451 25864 
30557 2136 55462 20308 35902 30238 21815 9255 48414 1956 27819 49185 
34428 59204 1955 10782 20077 59336 27867 29254 46219 28142 19108 52866 
39392 30683 40700 11760 7835 65096 22363 41318 9363 39016 34225 20539 
39956 47480 12499 49225 15360 18322 38157 61226 43010 39099 9631 49289 
40243 53645 10750 40712 32496 53093 2925 36166 60770 45263 30683 2537 
41922 56658 30762 49046 64446 11102 53481 43032 11576 31789 17015 47093 
44196 65248 30185 28250 27134 56704 42954 18203 36677 21296 22780 27224 
50771 19717 34434 16434 43648 57975 64581 51131 748 21266 26116 29653 
52032 13956 15378 8284 47951 24566 58583 61174 53515 1697 8710 46559 
54603 54603 54603 54603 54603 54603 54603 54603 54603 54603 54603 54603 
54603 54603 54603 54603 54603 54603 54603 54603 54603 54603 54603 54603 
54603 54603 54603 54603 54603 54603 54603 54603 54603 54603 54603 54603 
55683 26712 63891 36499 40089 58448 32114 14948 57516 35102 23239 45829 
62055 29107 10766 37551 30467 33145 4124 46208 60329 54800 29127 53398 
62990 41904 30506 58700 13996 24915 18279 54703 8346 29550 2794 19473 
64367 38250 23821 41639 16940 5076 26526 26796 23550 58420 10689 18614 
7471 34008 62429 27549 53162 37714 26394 37498 14193 15684 31649 31621 
7614 16389 59721 27793 58153 9808 61092 15071 42413 57890 33708 5530 
+0

ほとんどの「ランダム」関数は擬似乱数で、その種子と同じくらいです。あなたは少なくとも少しランダムな関数に何かを与えることができますか?たぶんカーソルの動き、または他の追跡不可能なもの? – jwsc

+1

また、 '/ dev/urandom'の代わりに'/dev/random'から読み込むこともできますが、適切なランダム性を与えるにはエントロピーが足りないときは前者がブロックされます。 http://stackoverflow.com/a/23712611/1220089を参照してください。実際には、すべてのことを傷つけてください。http://www.2uo.de/myths-about-urandom/ – ffledgling

+0

によれば、より良いシードだけが必要です。 '/ dev/urandom'について何を読んだのですか?なぜ、標準的な '/ dev'random'ではなく、本質的に信頼性の低いジェネレータを使用していますか?ヒント:単純なWikipedia検索で十分です。 – Olaf

答えて

3

でテスト

私はここで非常に間違って何かをやっていますか?

はい、コードは、read(myFile, &rand, 2)の戻り値を最初にチェックすることなく、randを使用しています。


コード読み取りに問題があるので、read()の戻り値をチェックしています。

if (read(myFile, &rand, 2) != 2) Handle_It(); 
else printf("%d " , (int) rand) ; 

いつも2ですか?私はコードがせっかちである疑いがある - のコードでは、単に待って、戻り値が1のとき可能な戻り値< 2は、部分的な結果を保存するときに再試行する必要があります(バイト配列を使用してください)


しかし、大規模で視点から見ると、たくさんのデータを取得すると"/dev/urandom"は、新しいアプローチをコードが使用することを指示します。 rapid乱数。 "/dev/urandom"はランダムビットを生成するのに時間がかかります。通常の方法は、PRNGのビットに"/dev/urandom"のビットを付けて、そのPRNGを呼び出すことです。

また、"/dev/random"と考えてください。


This postがさらに詳細に記載されている。

0

最終的にこれを追跡しました。 dev/urandomからの読み込みを繰り返すと結果が繰り返されるようです。解決策は、ファイルを閉じて再び開いたり、dev/urandomから1つの大きなチャンクを読み取ったりすることです。

+0

"dev/urandomからの繰り返し読み込みは結果を繰り返すようです" - >コードが繰り返し結果を受け取ったとき、 'read()'の戻り値は何ですか?戻り値が0のとき、 'read(myFile、&rand、2);'は結果を繰り返さず、単純に 'rand'を変更しませんでした。 – chux

+0

@chux実際には、それは0を返すことはありませんでした。私はあなたの答えの提案に従ってこれをチェックしました。 – camelccc

関連する問題