二項分布の半整数補正をJuliaで確認
はじめに
高校数学Bの「統計的な推測」の分野で,@kobayashi__renさんから次のようなポストがありました。
なんとなく,「Julia
で計算してみよう!」と思いスタートです。
問題と解答
問題を確認します。
まずは普通に解いてみます。
解答
解答はこうなると思いますが,天下り的ですね。
もう少し丁寧に
もう少し丁寧に作ってみます。
表の出る回数を
Julia
の累積分布関数cdf
を用いて
using Distributions # 分布パッケージ
2*(cdf(Normal(),1)-cdf(Normal(),0))
0.6826894921370861
Julia
の累積分布関数cdf
Julia
の累積分布関数cdf
は分布パッケージDistributions.jl
に入っています。
また,このDistributions.jl
では正規分布Normal
や二項分布Binomial
など様々な分布が利用できます。
Distributions.jl
パッケージ
累積分布関数cdf
正規分布Normal
二項分布Binomial
二項分布は正規分布に近似できるのか?
「Distributions.jl
に加えて,統計プロットパッケージStatsPlots.jl
を利用します。
using StatsPlots # 統計プロットパッケージ
dist1 = Binomial(100,0.5) # 二項分布B(100,0.5)
dist2 = Normal(50,sqrt(25)) # 正規分布N(50,5²)
plot(dist1 , label = "Binomial(100,0.5)")
plot!(dist2 , label = "Normal(50,5²)")
とてもいい感じです。近似してよさそうです。
今の時代,正規分布表まで戻らなくてもいいのではないか?
高校数学Bの教科書では、「標準正規分布とその表から値を求める」というのが流れです。しかし,今はPCなどで、誰もが二項分布のままでも確率の計算が容易にできます。「正規分布表まで戻らなくてもいいのではないか?」 となんとなく思ってきました。累積分布関数cdf
も標準正規分布
N(50,\,5^2) で確率を求める
正規分布dist2 = Normal(50,sqrt(25)) # 正規分布N(50,5²)
cdf(dist2,55)-cdf(dist2,45)
0.6826894921370861
もちろん大丈夫。
Bin(100,\,0.5) で確率を求める(その1)
二項分布dist1 = Binomial(100,0.5) # 二項分布B(100,0.5)
cdf(dist1,55)-cdf(dist1,45)
0.6802726792997346
これは,二項分布を連続的に拡張して累積分布関数を考えたもので,これもほぼ同じ値になります。
Bin(100,\,0.5) で確率を求める(その2)
二項分布(その1)は累積分布関数cdf
は連続関数であったので,本来の「離散的な確率」を定義から計算することにしました。数が大きくなるので,BigInt
を利用しました。
function f(m,n)
s::BigInt = 0
t::BigInt = 100
r = BigInt(2)^100
for i = m:n
s += binomial(t,i)
end
s/r
end
f(45,55)
0.728746975926165269296176250211956675803539260631347439581273484066059609176591
これは,今までの値からずれています。約68%から73%になっています。
半整数補正
𝕏でのやり取り
「ちょっとずれているので,みんなどう考えているんだろう?」と思い,𝕏にポストしました。
すぐに,@kaoru6さんと@Lenqthさんから 「半整数補正というのです」 と教えてもらいました。本当にありがたいです。
Webサイト
その後,Webサイトなどでも確認しました。
Juliaで計算の確認
- 正規分布表より
-
の累積分布関数よりN(0,1)
2*(cdf(Normal(),1.1)-cdf(Normal(),0))
0.7286678781072347
-
の累積分布関数よりN(50,5^2)
dist2 = Normal(50,sqrt(25)) # 正規分布N(50,5²)
cdf(dist2,55.5)-cdf(dist2,44.5)
0.7286678781072347
-
の累積分布関数よりBin(100,0.5)
dist1 = Binomial(100,0.5) # 二項分布B(100,0.5)
cdf(dist1,55.5)-cdf(dist1,44.5)
0.7287469759261653
どれも,離散的な二項分布で求めた確率とほぼ同じ(73%)となります。
Discussion
離散分布を連続分布に直して確率を求めるときに,もともと離散分布であったことを考えると,次のように考えると良さそうです。
julia
のDistributions.jl
では二項分布の累積密度関数に正則不完全ベータ関数を利用しているようです。cdf(dist1, 55) - cdf(dist1, 44) = 0.7287469759261653
cdf(dist2, 55) - cdf(dist2, 44) = 0.7262750758468348
となります。