aGrUM  0.16.0
chi2.cpp
Go to the documentation of this file.
1 
33 #include <agrum/core/math/chi2.h>
34 
35 #ifndef DOXYGEN_SHOULD_SKIP_THIS
36 
37 // constants used by Gary Perlman for his code for computing chi2 critical
38 // values
39 # define GUM_Z_MAX 6.0 // maximum meaningful z value
40 # define GUM_CHI_EPSILON 0.000001 // accuracy of critchi approximation
41 # define GUM_CHI_MAX 99999.0 // maximum chi square value
42 # define GUM_LOG_SQRT_PI \
43  0.5723649429247000870717135 // std::log (std::sqrt (pi))
44 # define GUM_I_SQRT_PI 0.5641895835477562869480795 // 1 / std::sqrt (pi)
45 # define GUM_BIGX 20.0 // max value to represent exp (x)
46 # define gum__ex(x) (((x) < -GUM_BIGX) ? 0.0 : std::exp(x))
47 
48 #endif /* DOXYGEN_SHOULD_SKIP_THIS */
49 
50 // include the inlined functions if necessary
51 #ifdef GUM_NO_INLINE
53 #endif /* GUM_NO_INLINE */
54 
55 namespace gum {
56 
57  // default constructor
58  Chi2::Chi2(const std::vector< std::size_t >& var_modalities,
59  double confidence_proba) :
60  __modalities(var_modalities),
61  __confidence_proba(confidence_proba) {
62  // for debugging purposes
63  GUM_CONSTRUCTOR(Chi2);
64  }
65 
66  // destructor
68  // for debugging purposes
69  GUM_DESTRUCTOR(Chi2);
70  }
71 
72  // computes the probability of normal z value (used by the cache)
73  double Chi2::__probaZValue(double z) {
74  double y, x, w;
75 
76  if (z == 0.0)
77  x = 0.0;
78  else {
79  y = 0.5 * std::fabs(z);
80 
81  if (y >= (GUM_Z_MAX * 0.5))
82  x = 1.0;
83  else if (y < 1.0) {
84  w = y * y;
85  x = ((((((((0.000124818987 * w - 0.001075204047) * w + 0.005198775019) * w
86  - 0.019198292004)
87  * w
88  + 0.059054035642)
89  * w
90  - 0.151968751364)
91  * w
92  + 0.319152932694)
93  * w
94  - 0.531923007300)
95  * w
96  + 0.797884560593)
97  * y * 2.0;
98  } else {
99  y -= 2.0;
100  x =
101  (((((((((((((-0.000045255659 * y + 0.000152529290) * y - 0.000019538132)
102  * y
103  - 0.000676904986)
104  * y
105  + 0.001390604284)
106  * y
107  - 0.000794620820)
108  * y
109  - 0.002034254874)
110  * y
111  + 0.006549791214)
112  * y
113  - 0.010557625006)
114  * y
115  + 0.011630447319)
116  * y
117  - 0.009279453341)
118  * y
119  + 0.005353579108)
120  * y
121  - 0.002141268741)
122  * y
123  + 0.000535310849)
124  * y
125  + 0.999936657524;
126  }
127  }
128 
129  return (z > 0.0 ? ((x + 1.0) * 0.5) : ((1.0 - x) * 0.5));
130  }
131 
132  // computes the probability of chi2 value (used by the cache)
133  double Chi2::probaChi2(double x, Size df) {
134  double a, y = 0, s;
135  double e, c, z;
136  int even; /* true if df is an even number */
137 
138  if ((x <= 0.0) || (df < 1)) return (1.0);
139 
140  a = 0.5 * x;
141 
142  even = (2 * (df / 2)) == df;
143 
144  if (df > 1) y = gum__ex(-a);
145 
146  s = (even ? y : (2.0 * __probaZValue(-std::sqrt(x))));
147 
148  if (df > 2) {
149  x = 0.5 * (df - 1.0);
150  z = (even ? 1.0 : 0.5);
151 
152  if (a > GUM_BIGX) {
153  e = (even ? 0.0 : GUM_LOG_SQRT_PI);
154  c = std::log(a);
155 
156  while (z <= x) {
157  e = std::log(z) + e;
158  s += gum__ex(c * z - a - e);
159  z += 1.0;
160  }
161 
162  return (s);
163  } else {
164  e = (even ? 1.0 : (GUM_I_SQRT_PI / std::sqrt(a)));
165  c = 0.0;
166 
167  while (z <= x) {
168  e = e * (a / z);
169  c = c + e;
170  z += 1.0;
171  }
172 
173  return (c * y + s);
174  }
175  } else
176  return (s);
177  }
178 
179  // computes the critical value of a given chi2 test (used by the cache)
180  double Chi2::__criticalValue(double proba, Size df) {
181  double minchisq = 0.0;
182  double maxchisq = GUM_CHI_MAX;
183  double chisqval;
184 
185  if (proba <= 0.0)
186  return (maxchisq);
187  else if (proba >= 1.0)
188  return (0.0);
189 
190  chisqval = df / std::sqrt(proba); /* fair first value */
191 
192  while (maxchisq - minchisq > GUM_CHI_EPSILON) {
193  if (probaChi2(chisqval, df) < proba)
194  maxchisq = chisqval;
195  else
196  minchisq = chisqval;
197 
198  chisqval = (maxchisq + minchisq) * 0.5;
199  }
200 
201  return (chisqval);
202  }
203 
204 } /* namespace gum */
static double __criticalValue(double proba, Size df)
Computes the critical value of a given chi2 test (used by the cache).
Definition: chi2.cpp:180
Copyright 2005-2019 Pierre-Henri WUILLEMIN et Christophe GONZALES (LIP6) {prenom.nom}_at_lip6.fr.
Definition: agrum.h:25
~Chi2()
Class destructor.
Definition: chi2.cpp:67
Represent the chi2 distribution.
Definition: chi2.h:58
static double probaChi2(double x, Size df)
Computes the probability of chi2 value.
Definition: chi2.cpp:133
Copyright 2005-2019 Pierre-Henri WUILLEMIN et Christophe GONZALES (LIP6) {prenom.nom}_at_lip6.fr.
Copyright 2005-2019 Pierre-Henri WUILLEMIN et Christophe GONZALES (LIP6) {prenom.nom}_at_lip6.fr.
Chi2(const std::vector< std::size_t > &var_modalities, double confidence_proba=GUM_LEARNING_CONFIDENCE_PROBA)
Default constructor.
Definition: chi2.cpp:58
std::size_t Size
In aGrUM, hashed values are unsigned long int.
Definition: types.h:48
static double __probaZValue(double z)
Computes the probability of normal z value.
Definition: chi2.cpp:73