JavaScript
正規乱数
/// <summary>正規乱数を生成するクラス</summary>
/// <param name="mu">平均</param>
/// <param name="sigma">偏差</param>
/// <code>標準正規分布にするには0,1を指定する。</code>
function NdrngObject(mu, sigma) {
// プライベート・フィールド
/// <summary>係数</summary>
var c = 0.0;
/// <summary>角</summary>
var theta = 0.0;
// 引数を指定しない、または両方にnullあるいはundefined
// あるいは不正な値を指定した場合は、
// 標準正規分布するようにmu = 0, sigma = 1とする。
if (isNaN(mu = parseFloat(mu))) {
mu = 0.0;
}
if (isNaN(sigma = parseFloat(sigma))) {
sigma = 1.0;
}
// プライベート・メソッド
/// <summary>常用対数の計算する。</summary>
/// <returns>10を底とする対数を返す。</returns>
function log10(x) {
return Math.log(x) / Math.LN10;
}
/// <summary>奇数回目の呼び出し。</summary>
/// <returns>次の正規乱数を返す。</returns>
function getNextAtOdd() {
// 係数Cとθを算出
c = Math.sqrt(-2 * log10(Math.random())) * sigma;
theta = 2 * Math.PI * Math.random();
// メソッドを入れ替える
this.getNext = getNextAtEven;
// 正規乱数を生成
return mu + c * Math.sin(theta);
}
/// <summary>偶数回目の呼び出し。</summary>
/// <returns>次の正規乱数を返す。</returns>
function getNextAtEven() {
// メソッドを入れ替える
this.getNext = getNextAtOdd;
// 計算しておいた係数Cとθを使って正規乱数を生成
return mu + c * Math.cos(theta);
// 意味合いとしては、2つの一様乱数を
// 2つの正規乱数に変換することになります。
}
// 公開メソッド
/// <summary>正規乱数を生成する。</summary>
/// <returns>次の正規乱数を返す。</summary>
this.getNext = getNextAtOdd;
}
仕様
- クラス名
- コンストラクタ
- プライベート・プロパティ(*1)
- プライベート・メソッド(*1)
- log10(x)
- 引数
- 戻り値
- 説明
- JavaScriptにはln()メソッドがないので、代わりです。
- getNextAtOdd()
- getNextAdEven()
- パブリック・メソッド
(*1) 通常、プライベート・メンバの記述は必要ありません。
このクラスを使って1000個の正規乱数を生成し、適当に集計したのが下のグラフで、ページを更新する度に生成します。ちょっと横長で見づらいのが難ですが、乱数っぽく、なかなかバラつきのある分布をすると思います。