0 | module Statistics.Norm.Rough
2 | import public Statistics.Norm
14 | [R] InvNormCDF where
16 | let res = if p == 0 then NegInf
17 | else if p == 1 then PosInf
18 | else if p < pLow then closeToLowBound p
19 | else if p.inv < pLow then - closeToLowBound p.inv
27 | closeToLowBound : Probability -> Double
28 | closeToLowBound p = let
29 | c1 = -7.784894002430293e-03
30 | c2 = -3.223964580411365e-01
31 | c3 = -2.400758277161838e+00
32 | c4 = -2.549732539343734e+00
33 | c5 = 4.374664141464968e+00
34 | c6 = 2.938163982698783e+00
36 | d1 = 7.784695709041462e-03
37 | d2 = 3.224671290700398e-01
38 | d3 = 2.445134137142996e+00
39 | d4 = 3.754408661907416e+00
41 | q = sqrt(-
2*log(p.asDouble))
43 | in (((((c1*q+c2)*q+c3)*q+c4)*q+c5)*q+c6) /
44 | ((((d1*q+d2)*q+d3)*q+d4)*q+1)
47 | middling : Probability -> Double
49 | a1 = -3.969683028665376e+01
50 | a2 = 2.209460984245205e+02
51 | a3 = -2.759285104469687e+02
52 | a4 = 1.383577518672690e+02
53 | a5 = -3.066479806614716e+01
54 | a6 = 2.506628277459239e+00
56 | b1 = -5.447609879822406e+01
57 | b2 = 1.615858368580409e+02
58 | b3 = -1.556989798598866e+02
59 | b4 = 6.680131188771972e+01
60 | b5 = -1.328068155288572e+01
62 | q = p.asDouble - 0.5
65 | in (((((a1*r+a2)*r+a3)*r+a4)*r+a5)*r+a6)*q /
66 | (((((b1*r+b2)*r+b3)*r+b4)*r+b5)*r+1)