2012-02-02 8 views
2

ユーザーが指定した辺の数でダイを回転させるプログラムを作成しました。問題は、あまりにも予測可能なことです。ダイスローリングプログラムは、すべてのランで乱数の同じシーケンスを生成します

私はCodeBlocks IDEを使用しています。コンパイラはGCCです。プログラムはデバッグビルドとリリースビルドの両方としてうまくコンパイルされますが、どのビルドオプションを選択しても実行時に毎回同じ値が返されます。私はこれを使うことはできません。意図した使い方は卓上RPGツールなので、ダイスが転がるパターンを知っていれば、スマートプレイヤーが不正行為をするのは比較的簡単です。

この問題を解決する最も簡単な方法は何ですか?ここで

はソースです:

#include <iostream>  /* for input and output */ 
#include <cstdlib>  /* for random numbers */ 

using namespace std; 

void rolldie() { 
    cout << "How many sides to the die?" << endl << "D"; 
    int die; 
    cin >> die; 
    int roll = rand() % die +1; 
    cout << endl << "The die rolled " << roll << endl << endl << "Roll another? (Y for yes, anything else for no; Capitalization counts) "; 
} 

int main() { 
    rolldie(); 
    char again; 
    cin >> again; 
    while (again == 89) { 
     rolldie(); 
     cin >> again; 
    } 
    return 0; 
} 
+3

あなたのコードにリンクしないでください - ここでそれを示しています。 –

+1

rand()を呼び出す前にsrand()を使用して乱数ジェネレータをシードします。 time()はまともな種を作る。 – Cameron

+0

どの乱数生成器を使用していますか?あなたは確かにそれを播種しなければなりませんが、あなたに*どのように*あなたに伝えるために、あなたは私たちにもっと詳細を与えなければなりません。 – Thilo

答えて

8

あなたの乱数ジェネレータをシードしませんでした。あなたのZIPファイルをダウンロードするつもりはありませんが、MinGWを使用しているので、おそらくsrandom(3)またはsrand(3)を調べたいと思うでしょう。

2

まず、CStdLib.Randは素晴らしいPRNGではありません。しかし、私はC++についてよく分かりませんが、C++の世界で何が良いのかを知るには十分です。私は、暗号化に推奨されるPRNGを見ていきます。これは、ほとんどの非セキュリティ目的で十分に機能するはずです。

さらに重要なことに、PRNGを「シード」していないことです。これは.NETのような他の言語の組み込みPRNGと同じように自動的には発生しません。シードされていない場合、シードは常に一定(おそらくはゼロ)なので、PRNGアルゴリズムによって生成される数値のストリームは常に同じになります。最も一般的なシードは、現在の時間に基づいています(できれば、「チック」の分解能であるため、呼び出しによって何ミリ秒の何分の一が取得されたか正確に推測することは困難です)。マウスカーソルの位置、RAMまたはHDDの最後にアクセスされたアドレス、または接続されたデバイスから利用可能な真のランダムデータが含まれます(オンラインカジノのサーバは、実際にランダムな環境データを提供する真のRNGデバイスを持つことがよくありますPRNGをシードするために使用することができる)。

2

http://www.boost.orgにアクセスし、乱数ジェネレータライブラリを入手してください。これは私が見た中で最も良いランダムジェネレータです。特にC + +の場合は、どこでもまともなものを見つけるのが本当に難しいです。

これらはC++のあらゆる種類のものにとって本当に素晴らしいライブラリのTONを持っているので、それらをブラウズすることを強くお勧めしますが、これは出力があまりにも予測可能であるという問題を解決するはずです。それを使用する方法の説明を読んで、ジェネレータを正しくシードするようにしてください。

ランダムジェネレータのシードに使用する限り、C++で使用する共通のものはtime(NULL)です(time.hまたはctimeにあります)。これはちょうど1970年1月1日からの現在の時間を表す数値を返します。プログラムが実行されるたびに異なる値を返すので、より単純な乱数に便利です。そして、これをブーストのランダムジェネレータと組み合わせると、よく見える。

0

単純な答え:

あなたの乱数ジェネレータは、それがそうで(時間のような)システム、ユーザー、ファイル、またはことが、いくつかのソースからの入力を毎回シードしたいです。

詳細な回答:

デフォルトの乱数生成器のrand()は、ほとんどのものに非常に平凡ですが、ランドに関するより詳細な答えのためにこれを参照してください。What's the Right Way to use the rand() Function in C++?

私の推薦:

マイ会社は、毎日予測不可能である必要がある乱数を扱い、メルセンヌ・ツイスター・アルゴリズムのバリエーションを使用し、ゲームでの使用に関しては、十分なパフォーマンスを見つけるでしょう。

追加ボーナスとして、CおよびC++でさまざまな形式で実装されているため、どのプロジェクトにも統合するのは非常に簡単です。例えば

http://www-personal.umich.edu/~wagnerr/MersenneTwister.html

か:http://www.math.sci.hiroshima-u.ac.jp/~m-mat/MT/SFMT/

関連する問題