rand(x, y, seed)
次のプロパティを使用して、引数に基づいて(疑似)乱数を返す関数に興味があります。
返される値は、その3つの引数に依存する必要があり、これまでに呼び出された回数には依存しません。
rand
たとえば、これらの呼び出しをこの順序で想定します。rand(0, 0, 123) = 1 rand(0, 1, 123) = 2 rand(0, 2, 123) = 3
次に、同じ引数を使用して呼び出し
rand
ますが、順序は異なりますが、同じ値を取得する必要があります。例えば:rand(0, 1, 123) = 2 rand(0, 2, 123) = 3 rand(0, 0, 123) = 1
関数は、通常の適切なプロパティ(まともな、私は実際にはそれほど凝ったものは必要ありません)PRNGを持っている必要があります:大周期、一様分布など。符号付き整数に適合する正の整数を返すことは問題ありません。必要に応じて高くすることもできます。
- これらの数値が行列の生成に使用されると想定します。次に、シードを変更することで、生成されたマトリックスが他のシードによって生成されたマトリックスと可能な限り異なって見えるようにする必要があります。これは、できるだけ多くのシードで発生するはずです。行列を繰り返さないようにします。
それが役に立ったら、私のシードは常にミリ秒単位のUNIXタイムスタンプになります(それがどういうわけか簡単になる場合は秒単位でもかまいません)。すべての引数は32ビットのsignedintまで使用できますが、関数内で64ビット値を操作することは問題ありません。
これにはどのような機能を使用できますか?
私が考えたこと:
パーリンノイズは私が望むことのいくつかを実行しているように見えますが、PRNGとして、特に分布に関して、それが実際にどれほど適切であるかはわかりません。(x, y)
また、パラメータがかなりランダムになり、すべてのパラメータを事前に計算できないため、どれほど効率的かわかりません。
次の関数も調べました。
p = 1400328593
rand(x, y, seed) = (x * x * seed + y * seed * seed + seed * x * y + seed) mod p
= (seed * (x * x + y * seed + x * y + 1)) mod p
これは十分な数を生成するようです。私の(非常に弱い)テストに基づくと、それらも非常によく分布しているようです。生理のテストはもっと難しいですが、私はそれをしていません。
アップデート:
上記の関数のEntの出力は次のとおりです。time(NULL)
シードはCで、値は次のように生成され(x, y) in {0 ... 999} x {0 ... 999}
ます。
エントロピー=バイトあたり3.312850ビット。
最適な圧縮により、この9207076バイトファイルのサイズが58%削減されます。
9207076サンプルのカイ2乗分布は、229710872.43であり、ランダムにこの値を超えるのは、0.01パーセント未満の時間です。
データバイトの算術平均値は52.3354(127.5 =ランダム)です。Piのモンテカルロ値は4.000000000(エラー27.32パーセント)です。シリアル相関係数は0.036131です(完全に無相関= 0.0)。
これは実際には十分に良いですか(理論的には、上記のテストはまったく良くないことを示唆しています)、または私が使用すべきよく知られているものがありますか?