############################ # 指数分布の計算 # coded by Y.Suganuma ############################ ########################################## # 指数分布の計算(P(X = x), P(X < x)) # x : データ # ram : 母数 # pr : P(X = x) # return : P(X < x) ########################################## def exponential(x, ram, pr) f = 0.0 if x < 0 pr[0] = 0.0 else y = Math.exp(-ram * x) pr[0] = ram * y f = 1.0 - y end return f end ############################################ # Newton法による非線形方程式(f(x)=0)の解 # x0 : 初期値 # eps1 : 終了条件1(|x(k+1)-x(k)|<eps1) # eps2 : 終了条件2(|f(x(k))|<eps2) # max : 最大試行回数 # ind : 実際の試行回数 # (負の時は解を得ることができなかった) # fn : f(x)とその微分を計算する関数名 # return : 解 # coded by Y.Suganuma ############################################ def newton(x0, eps1, eps2, max, ind, &fn) x1 = x0 x = x1 ind[0] = 0 sw = 0 while sw == 0 and ind[0] >= 0 sw = 1 ind[0] += 1 g = fn.call(0, x1) if g.abs() > eps2 if ind[0] <= max dg = fn.call(1, x1) if dg.abs() > eps2 x = x1 - g / dg if (x-x1).abs() > eps1 && (x-x1).abs() > eps1*x.abs() x1 = x sw = 0 end else ind[0] = -1 end else ind[0] = -1 end end end return x end ################################# # 関数値(f(x))とその微分の計算 ################################# exp_snx = Proc.new { |sw, x| if sw == 0 $p - Math.exp(-$ram * x) else $ram * Math.exp(-$ram * x) end } # 密度関数と分布関数の値 print("母数は? ") $ram = Float(gets()) print("目的とする結果は?\n") print(" =0 : 確率の計算( P(X = x) 及び P(X < x) の値)\n") print(" =1 : p%値( P(X > u) = 0.01p となるuの値) ") sw = Integer(gets()) pr = Array.new(1) if sw == 0 print("グラフ出力?(=1: yes, =0: no) ") sw = Integer(gets()) if sw == 0 # 密度関数と分布関数の値 print(" データは? ") x = Float(gets()) f = exponential(x, $ram, pr) print("P(X = " + String(x) + ") = " + String(pr[0]) + ", P( X < " + String(x) + ") = " + String(f) + " (母数 = " + String($ram) + ")\n") # グラフ出力 else print(" 密度関数のファイル名は? ") file1 = gets().strip() print(" 分布関数のファイル名は? ") file2 = gets().strip() print(" データの上限は? ") up = Integer(gets()) print(" 刻み幅は? ") h = Float(gets()) out1 = open(file1, "w") out2 = open(file2, "w") x = 0 while x < up+0.5*h f = exponential(x, $ram, pr) out1.print(String(x) + " " + String(pr[0]) + "\n") out2.print(String(x) + " " + String(f) + "\n") x += h end out1.close() out2.close() end # %値 else print("%の値は? ") x = Float(gets()) $p = 0.01 * x if $p < 1.0e-7 print(String(x) + "%値 = ∞ (母数 = " + String($ram) + ")\n") else ok = Array.new(1) f = newton(0.0, 1.0e-6, 1.0e-10, 100, ok, &exp_snx) print(String(x) + "%値 = " + String(f) + " (母数 = " + String($ram) + ")\n") end end