私は周りを見回してきましたが、それを行う方法がわかりません。
私は見つけました このページ これは最後の段落で次のように述べています:
ポアソン分布から取得した乱数の単純なジェネレーターは、次の単純なレシピを使用して取得されます。ifx1、 バツ2、...は、0と1の間で一様分布する乱数のシーケンスです。kは、積xの最初の整数です。1 ・ バツ2 ・ ... ・ バツk + 1 <e-λ
別のページ 二項数の生成方法を説明しているのを見つけましたが、ポアソン生成の近似を使用していると思います。これは役に立ちません。
たとえば、二項乱数について考えてみます。二項乱数は、コインのN回のトスにおける頭の数であり、任意の1回のトスでの頭の確率pです。区間(0,1)でN個の一様乱数を生成し、p未満の数をカウントする場合、カウントはパラメーターNおよびpを持つ二項乱数です。
私はそれを行うためのライブラリがあることを知っていますが、それらを使用することはできません。言語(この場合はJava)によって提供される標準の一様ジェネレータのみです。
これが ウィキペディアがクヌースがそうするように言っている方法 :
init:
Let L ← e^(−λ), k ← 0 and p ← 1.
do:
k ← k + 1.
Generate uniform random number u in [0,1] and let p ← p × u.
while p > L.
return k − 1.
Javaでは、次のようになります。
public static int getPoisson(double lambda) {
double L = Math.exp(-lambda);
double p = 1.0;
int k = 0;
do {
k++;
p *= Math.random();
} while (p > L);
return k - 1;
}
の第10章を通過します不均一確率変数の生成 (PDF) Luc Devroye(私は ウィキペディアの記事 からリンクされていることがわかりました)はこれを与えます:
public static int getBinomial(int n, double p) {
int x = 0;
for(int i = 0; i < n; i++) {
if(Math.random() < p)
x++;
}
return x;
}
これらのアルゴリズムはどちらも最適ではありません。 1つ目はO(λ)、2つ目はO(n)です。これらの値の通常の大きさ、およびジェネレーターを呼び出す必要がある頻度によっては、より優れたアルゴリズムが必要になる場合があります。上記にリンクしているペーパーには、一定時間で実行されるより複雑なアルゴリズムがありますが、これらの実装は読者の演習として残しておきます。 :)
これと他の数値問題のために、聖書は数値レシピ本です。
ここにCの無料バージョンがあります: http://www.nrbook.com/a/bookcpdf.php (プラグインが必要です)
または、Googleブックスで確認できます: http://books.google.co.uk/books?id=4t-sybVuoqoC&lpg=PP1&ots=5IhMINLhHo&dq=numerical%20recipes%20in%20c&pg=PP1#v=onepage&q =&f = false
CコードはJavaへの転送が非常に簡単である必要があります。
この本は、多くの数値問題のために金でその重さの価値があります。上記のサイトでは、最新版の本を購入することもできます。
Kipによって投稿された回答は、到着率(ラムダ)が小さいポアソンRVを生成するのに完全に有効ですが、ウィキペディアに投稿された2番目のアルゴリズム ポアソン確率変数の生成 は、数値的安定性のため、到着率が高い場合に適しています。
このため、ラムダが非常に高いポアソンRVの生成を必要とするプロジェクトの1つを実装しているときに、問題が発生しました。だから私は別の方法を提案します。
これをbuild.gradleに追加できます
implementation 'org.kie.modules:org-Apache-commons-math:6.5.0.Final'
クラスを使用しますPoissonDistributionクラスPoissonDistributionの詳細
次のライブラリ(Javaコード)には、CERNからのいくつかの実装があります。
http://acs.lbl.gov/~hoschek/colt/
二項乱数については、1988年の論文「二項確率変量生成」に基づいており、最適化されたアルゴリズムを使用しているのでお勧めします。
よろしく