# grand

乱数生成器

## 呼び出し手順

    Y=grand(m, n, dist_type [,p1,...,pk])
                Y=grand(X, dist_type [,p1,...,pk])
                Y=grand(n, dist_type [,p1,...,pk])
                S=grand(action [,q1,....,ql])

## パラメータ

m, n

  整数, 出力行列 `Y`の大きさ

X

  次元(つまり`mx n`) のみ使用される行列

dist_type

  生成する変量の分布の種類('bin', 'nor', 'poi', ...)を指定する文字列

p1, ..., pk

  分布`dist_type`を完全に定義するために必要なパラメータ (実数または整数)

Y

  `mx n` ランダム出力行列

action

  基底生成器に指定する処理を記述する文字列 (カレントの基底生成器を変更するには'setgen', カレントの基底生成器の名前を取得するには 'getgen', カレントの基底生成器の状態(シード)を取得するには 'getsd',など...)

q1, ..., ql

  処理を定義するためにひるようなパラメータ (通常は1つの文字列)

S

  処理の出力 (通常は文字列または実数の列ベクトル)

## 説明

警告: シードを指定しない場合,系列はあるセッションと別のセッションで 同一のままとなります.

rand関数を使用する各スクリプトの初めに, 以下を実行する必要があります:

    rand('seed',getdate('s'))

この関数は種々の分布により乱数を生成する際に使用することができます. この場合,`m x n`行列を得るには 最初の形式が異なる3種類の呼び出し手順のどれかを適用する必要があります. `X` が `m x n`行列の 場合,最初の2つの形式は等価で,3番目の形式は '多値'分布(例えば,多項分布,多変量分布,ガウス分布, etc...)に対応します. この際,サンプルは列ベクトル(つまり,次元`m`)で, そのような`n`個の乱数ベクトル (つまり`m x n` 行列)が得られます.

最後の形式は基底生成器を変更(v2.7以降基底生成器を選択できます) したり,内部の状態(シード)を変更または取得したり,... といった基底生成器への 種々の操作を行う際に使用されます.

これらの基底生成器はランダムな整数を 大きな整数区間(lgi)上の一様分布に従い, 他の全ての分布はそこから取得されます. (一般にはあるスキーム lgi -> U([0,1)) -> 指定する分布)

## 指定された分布から乱数を取得する

ベータ分布

  `Y=grand(m,n,'bet',A,B)` は パラメータ`A` およびd `B` を指定したベータ分布からランダム変量を生成します. ベータ分布の密度は (0 < x < 1) です:

  \dfrac{x^{A-1}(1-x)^{B-1}}{\beta(A,B)}

  `A` および `B` は 実数で >10^{-37}とします. 関係する関数は : cdfbetです.

二項分布

  `Y=grand(m,n,'bin',N,p)` は パラメータ`N` (正の整数) および `p` ([0,1]の範囲の実数)を指定した二項分布に基づきランダム変量を生成します. この分布では,成功する確率が`p`の `N`回の独立なベルヌーイ試行における 成功回数となります. 関係する関数: binomial, cdfbin.

負の二項分布

  `Y=grand(m,n,'nbn',N,p)` は パラメータ`N` (正の整数) および`p` ( (0,1)の実数)を指定した負の二項分布に基づきランダム変量を生成します : 成功確率 `p`の独立なベルヌーイ試行において `N`回成功する前に発生する失敗の回数. 関係する関数 : cdfnbn.

カイ二乗分布

  `Y=grand(m,n,'chi', Df)` は,自由度 `Df`(実数 > 0.0)を指定した カイ二乗分布に基づくランダム変量を生成します. 関係する関数: cdfchi.

非心カイ二乗分布

  `Y=grand(m,n,'nch',Df,Xnon)` は, 自由度`Df`(実数 > 0.0)および 非心度パラメータ`Xnonc` (実数 >= 0.0) を指定した非心カイ二乗分布に基づくランダム変量を生成します. 関係する関数 : cdfchn.

指数分布

  `Y=grand(m,n,'exp',Av)` は 平均`Av`(実数 >= 0.0) を指定した指数分布に基づくランダム変量を生成します.

F分布

  `Y=grand(m,n,'f',Dfn,Dfd)` は, 分子の自由度`Dfn` (実数 > 0.0) および 分母の自由度`Dfd` (実数 > 0.0) を指定した F(分散比)分布に基づくランダム変量を生成します. 関係する関数 : cdff.

非心F分布

  `Y=grand(m,n,'nf',Dfn,Dfd,Xnon)`は, 分子の自由度`Dfn` (実数 >= 1), および 分母の自由度`Dfd` (実数 > 0) , および非心パラメータ `Xnonc` (実数 >= 0)を指定して 非心F分布に基づくランダム変量を生成します. 関係する関数 : cdffnc.

ガンマ分布

  `Y=grand(m,n,'gam',shape,rate)` は,パラメータ`shape` (実数 > 0)および `rate` (実数 > 0)を指定して ガンマ分布に基づくランダム変量を生成します. ガンマの密度は以下となります :

  \dfrac{ \textrm{rate}^{\textrm{shape}} x^{\textrm{shape}-1} e^{-\textrm{rate} x}}{\gamma(\textrm{shape}) }

  関係する関数 : gamma, cdfgam.

ガウスラプラス(正規)分布

  `Y=grand(m,n,'nor',Av,Sd)` は 平均`Av` (実数) および標準偏差 `Sd` (実数 >= 0)の 正規分布に基づくランダム変量を生成します. 関係する関数 : cdfnor.

多変量ガウス(多変量正規)分布

  `Y=grand(n,'mn',Mean,Cov)`は, `n`次の多変量正規ランダム変量を 生成します; `Mean` は `m x 1` 行列, `Cov`は `m x m` 対称正定行列です (`Y` はこの場合 `m x n` 行列となります).

幾何分布

  `Y=grand(m,n,'geom', p)` は, パラメータ`p`を指定した 幾何分布に基づくランダム変量を生成します: (成功率`p`の)ベルヌーイ試行に1回成功するまでの回数. `p` は [p_{min},1] ( p_{min} = 1{,}3\times 10^{-307} )の範囲とします.

  `Y` は整数の値を有する正の実数となり, これらは "1回の成功を得る時の試行回数"です.

マルコフ分布

  `Y=grand(n,'markov',P,x0)` は, 推移行列 `P`で記述されたマルコフ連鎖の `n`個の一連の状態量を生成します. 状態量の初期値は`x0`で指定されます. `x0`が大きさ`m=size(x0,'*')`の 行列の場合,`Y`は大きさ`m x n` の行列となります. `Y(i,:)` は初期状態量`x0(i)` から得られるサンプルパスです.

多項分布

  `Y=grand(n,'mul',nb,P)` は, 多項分布に基づき`n`個の観測量を生成します: `m`個のカテゴリの中に `nb`個の分類のイベント (`m`個の"boxes"の中に`nb`個の"balls"). `P(i)`はあるイベントがカテゴリ i に分類される確率です. 確率ベクトル`P`の大きさは`m-1`です (カテゴリ`m`の確率は`1-sum(P)`となります). `Y` の大きさは `m x n`で, 各列 `Y(:,j)` は多項分布の観測量, `Y(i,j)`は( `j`番目の観測値に関する)カテゴリ`i`に 分類されるイベントの数です(`sum(Y(:,j)) = nb` ).

ポワソン分布

  `Y=grand(m,n,'poi',mu)`は, 平均 `mu (実数 >= 0.0)`のポワソン分布に基づき 乱数を生成します. 関係する機能 : cdfpoi.

ランダム置換

  `Y=grand(n,'prm',vect)` は, 列ベクトル (`m x 1`) `vect`の`n`個の ランダム置換を生成します.

一様分布 (def)

  `Y=grand(m,n,'def')` は, は,`[0,1)` (1は含まれません) の範囲の 一様分布に基づきランダム変量を生成します.

一様分布 (unf)

  `Y=grand(m,n,'unf',Low,High)` は `[Low, High)` の範囲の一様分布に基づく の実数のランダム変量を生成します.

一様分布 (uin)

  `Y=grand(m,n,'uin',Low,High)`は, `Low` および `High` (含む) の範囲の一様分布に基づく の整数のランダム変量を生成します. `High` および `Low` は (\textrm{High}-\textrm{Low}+1) < 2\,147\,483\,561の 範囲の整数とする必要があります.

一様分布 (lgi)

  `Y=grand(m,n,'lgi')` は カレントの生成器の基底出力として 以下の範囲の一様分布に基づくランダムな整数を返します:

  - mt, kiss および fsultra の場合は `[0, 2^32 - 1]`

  - clcg2 の場合は `[0, 2147483561]`

  - clcg4の場合は `[0, 2^31 - 2]`

  - urandの場合は `[0, 2^31 - 1]`.

## カレントの生成器およびその状態を設定/取得

Scilab-2.7以降,異なる('lgi'分布に基づくランダムな整数,もしくは その整数に基づき得られたもの)基底生成器を選択することが 可能となっています:

mt

  周期`2^19937`の M. Matsumoto および T. NishimuraのMersenne-Twister, 状態は `624`個の整数の配列(およびこの配列のインデックス)により 指定されます; これがデフォルトの生成器です.

kiss

  周期`2^123`のG. MarsagliaのKeep It Simple Stupid, 状態は`4`個の整数により指定されます.

clcg2

  周期 `2^61`のP. L'Ecuyerの2線形共役合同生成器, 状態は`2`個の整数により指定されます; grandにより以前に(若干修正された)使用されていた生成器です.

clcg4

  周期 `2^121`のP. L'Ecuyerの4線形合同生成器, 状態は`4`個の整数により指定されます; この生成器は`101`個の(重ならない)異なる生成器に 分割することができ,異なるタスクの場合に有用です ('clcg4に固有の動作'および 'clcg4のテスト例'を参照).

urand

  scilab 関数 randで使用される生成器, `1`個の整数で状態が定義され, 周期は`2^31` (d.e. knuth (1969), vol 2. State に示された理論と提案に基づく). これはこの一覧の中では高速ですが, やや古臭くなっています (重要なシミュレーションでは使用しないでください).

fsultra

  Arif Zaman および George Marsagliaの合同生成器に基づく Subtract-with-Borrow 生成器, 周期は `10^356`以上, 状態は37個の整数の配列(およびこの配列へのインデックス, フラグ (0または1)および他の整数)により指定されます.

全ての生成器に共通なアクションの動作を以下に示します:

action= 'getgen'

  `S=grand('getgen')` はカレントの基底生成器を返します ( `S` は以下の文字列のどれかです: 'mt', 'kiss', 'clcg2', 'clcg4', 'urand', 'fsultra'.

action= 'setgen'

  `grand('setgen',gen)`は カレントの基底生成器を`gen`に設定します. この文字列には 'mt', 'kiss', 'clcg2', 'clcg4', 'urand', 'fsultra' のどれかを指定します( このコールは新しいカレントの生成器を返すことに注意してください).

action= 'getsd'

  `S=grand('getsd')` はカレントの基底生成器の カレントの状態 (カレントのシード)を返します ; `S` には, mt の場合は`625`次 (先頭は`[1,624]`の範囲のインデックスです), kiss の場合は `4` 次, clcg2の場合は `2`次, fsultraの場合は `40` , clcg4 の場合は `4`次 (最後の1つについてはカレントの仮想生成器のカレントの状態が取得されます), および urand の場合は `1`次 の(整数)列ベクトルが出力されます.

action= 'setsd'

  `grand('setsd',S), grand('setsd',s1[,s2,s3,s4])` は カレントの基底生成器の状態(新しいシード)を設定します:

  mtの場合

    `S`は`625`次の整数ベクトル (最初の要素はインデックスで`[1,624]`の範囲とする 必要があります, 続く`624`個の要素は `[0,2^32[`)の範囲とします) (しかし,全てをゼロにするすることはできません)； 整数`s1`を1つだけ指定することで,より簡単に初期化を 行うことができます. (`s1` は `[0,2^32[`の範囲とします) ;

  kissの場合

    `[0,2^32[`の範囲の `4` 個の整数 `s1,s2, s3,s4` を指定します ;

  clcg2の場合

    `2` 個の整数 `s1` (範囲:`[1,2147483562]`) および `s2` (範囲: `[1,2147483398]`) を指定します ;

  clcg4の場合

    `4` 個の整数 `s1` (範囲: `[1,2147483646]`), `s2` (範囲: `[1,2147483542]`), `s3` (範囲: `[1,2147483422]`), `s4` (範囲: `[1,2147483322]` ) を指定します ; `注意` : clcg4の場合, カレントの仮想生成器のシードを設定しますが, この生成器と他の仮想生成器との間の同期が失われる可能性があります. すなわち,生成されるデータ列は他の生成器により生成されるデータ列と オーバーラップしていないということは保証されません)　=> 代わりに 'setall' オプションを使用してください.

  urandの場合

    `[0,2^31`[の範囲の`1` 個の整数 `s1` を指定します.

  fsultraの場合

    `S` は`40`次の整数ベクトルで, (最初の要素はインデックスで`[0,37]`の範囲とします, 2番目の要素はフラグ (0または1),3番目は[1,2^32[ の範囲の整数, 367個のその他の整数(範囲: [0,2^32[))); `[0,2^32[`の範囲の 整数を2つだけ (`s1` および `s2`) 指定することでより簡単に(そして推奨される)初期化を行うことができます.

action= 'phr2sd'

  `Sd=grand('phr2sd', phrase)` は, 基底生成器(clcg2に適しています)の状態を変更するシードとして使用可能な `1 x 2` ベクトル `Sd`を生成する `phrase` (文字列)を指定します.

## clcg4の固有のオプション

clcg4 生成器は他の生成器と同時に使用することができますが, 系列がオーバーラップしない 複数(`101`個)の仮想生成器に分割できるという利点があります. (古典的な生成器を使用する場合,異なる系列を得るために 初期状態量(シード)を別のものに変更できますが,完全に異なる系列となることは 保証されません) 各仮想生成器は`2^72` 個の値の系列に対応します. これらはさらに長さ`W=2^41`の`V=2^31`個の セグメント(またはブロック)に分割されます. 指定した仮想生成器について,系列の先頭またはカレントのセグメントの先頭に戻るか 次のセグメントに直接移動するかを選択できます. 'setall'オプションにより生成器 `0` の初期状態(シード)を 変更することも可能です. これにより,同期をとるために他の仮想生成器の初期状態量を変更することも可能です. (すなわち, gen `0` の新しい初期状態の関数として, gen `1..100` の初期状態量は`101`個の 重複しない系列が得られるように再計算されます.)

action= 'setcgn'

  `grand('setcgn',G)` は clcg4 のカレントの仮想生成器を設定します (clcg4 が設定された時, この値は使用される仮想 (clcg4)生成器の数`G`となります); 仮想 clcg4 生成器は`0,1,..,100`と番号付けられます (そして, `G`は`[0,100]`の範囲の整数となります); デフォルトで,カレントの仮想生成器は`0`です.

action= 'getcgn'

  `S=grand('getcgn')` はカレントの仮想 clcg4 生成器の数を返します.

action= 'initgn'

  `grand('initgn',I)` はカレントの仮想生成器の状態を再度初期化します

  I = -1

    初期シードの状態を設定します

  I = 0

    直近の(前の)シードを設定します (つまり,カレントのセグメントの先頭)

  I = 1

    直近のシード(すなわち,次のセグメントの先頭)から新しいシード`W`に 状態量を設定し,カレントのセグメントのパラメータをリセットします.

action= 'setall'

  `grand('setall',s1,s2,s3,s4)` は 生成器`0`の初期状態を`s1,s2,s3,s4`に設定します. 他の生成器の初期シードは同期がとれるように設定されます. `s1, s2, s3, s4`に関する制約については,'setsd'アクションを参照ください.

action= 'advnst'

  `grand('advnst',K)` はカレントの生成器の状態を `2^K`だけ前に進め,初期シードをその値でリセットします.

## clcg4のテスト例

clcg4 の分割機能の適用例を以下に示します. 2つの統計上のテクニックを異なるデータの大きさで比較します. 最初の手法では,ブートストラップ手法を使用し,しらみつぶし法のみを適用する 2番目の手法よりも少ないデータで同等の精度が得られると考えられます. 最初の方法の場合,25および50の間に一様分布する大きさのデータ集合が生成されます. その後,指定した大きさのデータ集合が生成され,解析されます. 2番目の方法は, 100および200の間の大きさのデータ集合を選択し,データを生成し,解析します. この過程を1000回繰り返します. 分散を減少させるために,2つの手法で使用される乱数を1000回の比較の各回で 同じとすることが望まれます. しかし,2番目の手法は1番目の手法よりも多くの乱数を使用し, このパッケージなしでは同期は困難となります. clcg4 ではこれは容易です. 生成器 0 を使用し最初の手法のサンプルの大きさを取得し, 生成器 1 をデータを得る際に使用します. 次にカレントのブロックの先頭に状態をリセットし, 2番目の手法にも同様のことをします. これにより,2番目の手法で使用される初期データが1番目の手法で使用されることが 保証されます. 両方の処理が完了した時,両方の生成器のブロックを前に進めます.

## 参照

- rand