skew_normal_example.cpp 8.0 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275
  1. // Copyright Benjamin Sobotta 2012
  2. // Use, modification and distribution are subject to the
  3. // Boost Software License, Version 1.0. (See accompanying file
  4. // LICENSE_1_0.txt or copy at http://www.boost.org/LICENSE_1_0.txt)
  5. #ifdef _MSC_VER
  6. # pragma warning (disable : 4512) // assignment operator could not be generated
  7. # pragma warning (disable : 4127) // conditional expression is constant.
  8. #endif
  9. #include <boost/math/distributions/skew_normal.hpp>
  10. using boost::math::skew_normal_distribution;
  11. using boost::math::skew_normal;
  12. #include <iostream>
  13. #include <cmath>
  14. #include <utility>
  15. void check(const double loc, const double sc, const double sh,
  16. const double * const cumulants, const std::pair<double, double> qu,
  17. const double x, const double tpdf, const double tcdf)
  18. {
  19. using namespace boost::math;
  20. skew_normal D(loc, sc, sh);
  21. const double sk = cumulants[2] / (std::pow(cumulants[1], 1.5));
  22. const double kt = cumulants[3] / (cumulants[1] * cumulants[1]);
  23. // checks against tabulated values
  24. std::cout << "mean: table=" << cumulants[0] << "\tcompute=" << mean(D) << "\tdiff=" << fabs(cumulants[0]-mean(D)) << std::endl;
  25. std::cout << "var: table=" << cumulants[1] << "\tcompute=" << variance(D) << "\tdiff=" << fabs(cumulants[1]-variance(D)) << std::endl;
  26. std::cout << "skew: table=" << sk << "\tcompute=" << skewness(D) << "\tdiff=" << fabs(sk-skewness(D)) << std::endl;
  27. std::cout << "kur.: table=" << kt << "\tcompute=" << kurtosis_excess(D) << "\tdiff=" << fabs(kt-kurtosis_excess(D)) << std::endl;
  28. std::cout << "mode: table=" << "N/A" << "\tcompute=" << mode(D) << "\tdiff=" << "N/A" << std::endl;
  29. const double q = quantile(D, qu.first);
  30. const double cq = quantile(complement(D, qu.first));
  31. std::cout << "quantile(" << qu.first << "): table=" << qu.second << "\tcompute=" << q << "\tdiff=" << fabs(qu.second-q) << std::endl;
  32. // consistency
  33. std::cout << "cdf(quantile)=" << cdf(D, q) << "\tp=" << qu.first << "\tdiff=" << fabs(qu.first-cdf(D, q)) << std::endl;
  34. std::cout << "ccdf(cquantile)=" << cdf(complement(D,cq)) << "\tp=" << qu.first << "\tdiff=" << fabs(qu.first-cdf(complement(D,cq))) << std::endl;
  35. // PDF & CDF
  36. std::cout << "pdf(" << x << "): table=" << tpdf << "\tcompute=" << pdf(D,x) << "\tdiff=" << fabs(tpdf-pdf(D,x)) << std::endl;
  37. std::cout << "cdf(" << x << "): table=" << tcdf << "\tcompute=" << cdf(D,x) << "\tdiff=" << fabs(tcdf-cdf(D,x)) << std::endl;
  38. std::cout << "================================\n";
  39. }
  40. int main()
  41. {
  42. using namespace boost::math;
  43. double sc = 0.0,loc,sh,x,dsn,qsn,psn,p;
  44. std::cout << std::setprecision(20);
  45. double cumulants[4];
  46. /* R:
  47. > install.packages("sn")
  48. Warning in install.packages("sn") :
  49. 'lib = "/usr/lib64/R/library"' is not writable
  50. Would you like to create a personal library
  51. '~/R/x86_64-unknown-linux-gnu-library/2.12'
  52. to install packages into? (y/n) y
  53. --- Please select a CRAN mirror for use in this session ---
  54. Loading Tcl/Tk interface ... done
  55. also installing the dependency mnormt
  56. trying URL 'http://mirrors.dotsrc.org/cran/src/contrib/mnormt_1.4-5.tar.gz'
  57. Content type 'application/x-gzip' length 34049 bytes (33 Kb)
  58. opened URL
  59. ==================================================
  60. downloaded 33 Kb
  61. trying URL 'http://mirrors.dotsrc.org/cran/src/contrib/sn_0.4-17.tar.gz'
  62. Content type 'application/x-gzip' length 65451 bytes (63 Kb)
  63. opened URL
  64. ==================================================
  65. downloaded 63 Kb
  66. > library(sn)
  67. > options(digits=22)
  68. > sn.cumulants(1.1, 2.2, -3.3)
  69. [1] -0.5799089925398568 2.0179057767837230 -2.0347951542374196
  70. [4] 2.2553488991015072
  71. > qsn(0.3, 1.1, 2.2, -3.3)
  72. [1] -1.180104068086876
  73. > psn(0.4, 1.1, 2.2, -3.3)
  74. [1] 0.733918618927874
  75. > dsn(0.4, 1.1, 2.2, -3.3)
  76. [1] 0.2941401101565995
  77. */
  78. //1 st
  79. loc = 1.1; sc = 2.2; sh = -3.3;
  80. std::cout << "location: " << loc << "\tscale: " << sc << "\tshape: " << sh << std::endl;
  81. cumulants[0] = -0.5799089925398568;
  82. cumulants[1] = 2.0179057767837230;
  83. cumulants[2] = -2.0347951542374196;
  84. cumulants[3] = 2.2553488991015072;
  85. x = 0.4;
  86. p = 0.3;
  87. qsn = -1.180104068086876;
  88. psn = 0.733918618927874;
  89. dsn = 0.2941401101565995;
  90. check(loc, sc, sh, cumulants, std::make_pair(p,qsn), x, dsn, psn);
  91. /* R:
  92. > sn.cumulants(1.1, .02, .03)
  93. [1] 1.1004785154529559e+00 3.9977102296128255e-04 4.7027439329779991e-11
  94. [4] 1.4847542790693825e-14
  95. > qsn(0.01, 1.1, .02, .03)
  96. [1] 1.053964962950150
  97. > psn(1.3, 1.1, .02, .03)
  98. [1] 1
  99. > dsn(1.3, 1.1, .02, .03)
  100. [1] 4.754580380601393e-21
  101. */
  102. // 2nd
  103. loc = 1.1; sc = .02; sh = .03;
  104. std::cout << "location: " << loc << "\tscale: " << sc << "\tshape: " << sh << std::endl;
  105. cumulants[0] = 1.1004785154529559e+00;
  106. cumulants[1] = 3.9977102296128255e-04;
  107. cumulants[2] = 4.7027439329779991e-11;
  108. cumulants[3] = 1.4847542790693825e-14;
  109. x = 1.3;
  110. p = 0.01;
  111. qsn = 1.053964962950150;
  112. psn = 1;
  113. dsn = 4.754580380601393e-21;
  114. check(loc, sc, sh, cumulants, std::make_pair(p,qsn), x, dsn, psn);
  115. /* R:
  116. > sn.cumulants(10.1, 5, -.03)
  117. [1] 9.980371136761052e+00 2.498568893508016e+01 -7.348037395278123e-04
  118. [4] 5.799821402614775e-05
  119. > qsn(.8, 10.1, 5, -.03)
  120. [1] 14.18727407491953
  121. > psn(-1.3, 10.1, 5, -.03)
  122. [1] 0.01201290665838824
  123. > dsn(-1.3, 10.1, 5, -.03)
  124. [1] 0.006254346348897927
  125. */
  126. // 3rd
  127. loc = 10.1; sc = 5; sh = -.03;
  128. std::cout << "location: " << loc << "\tscale: " << sc << "\tshape: " << sh << std::endl;
  129. cumulants[0] = 9.980371136761052e+00;
  130. cumulants[1] = 2.498568893508016e+01;
  131. cumulants[2] = -7.348037395278123e-04;
  132. cumulants[3] = 5.799821402614775e-05;
  133. x = -1.3;
  134. p = 0.8;
  135. qsn = 14.18727407491953;
  136. psn = 0.01201290665838824;
  137. dsn = 0.006254346348897927;
  138. check(loc, sc, sh, cumulants, std::make_pair(p,qsn), x, dsn, psn);
  139. /* R:
  140. > sn.cumulants(-10.1, 5, 30)
  141. [1] -6.112791696741384 9.102169946425548 27.206345266148194 71.572537838642916
  142. > qsn(.8, -10.1, 5, 30)
  143. [1] -3.692242172277
  144. > psn(-1.3, -10.1, 5, 30)
  145. [1] 0.921592193425035
  146. > dsn(-1.3, -10.1, 5, 30)
  147. [1] 0.0339105445232089
  148. */
  149. // 4th
  150. loc = -10.1; sc = 5; sh = 30;
  151. std::cout << "location: " << loc << "\tscale: " << sc << "\tshape: " << sh << std::endl;
  152. cumulants[0] = -6.112791696741384;
  153. cumulants[1] = 9.102169946425548;
  154. cumulants[2] = 27.206345266148194;
  155. cumulants[3] = 71.572537838642916;
  156. x = -1.3;
  157. p = 0.8;
  158. qsn = -3.692242172277;
  159. psn = 0.921592193425035;
  160. dsn = 0.0339105445232089;
  161. check(loc, sc, sh, cumulants, std::make_pair(p,qsn), x, dsn, psn);
  162. /* R:
  163. > sn.cumulants(0,1,5)
  164. [1] 0.7823901817554269 0.3878656034927102 0.2055576317962637 0.1061119471655128
  165. > qsn(0.5,0,1,5)
  166. [1] 0.674471117502844
  167. > psn(-0.5, 0,1,5)
  168. [1] 0.0002731513884140924
  169. > dsn(-0.5, 0,1,5)
  170. [1] 0.00437241570403263
  171. */
  172. // 5th
  173. loc = 0; sc = 1; sh = 5;
  174. std::cout << "location: " << loc << "\tscale: " << sc << "\tshape: " << sh << std::endl;
  175. cumulants[0] = 0.7823901817554269;
  176. cumulants[1] = 0.3878656034927102;
  177. cumulants[2] = 0.2055576317962637;
  178. cumulants[3] = 0.1061119471655128;
  179. x = -0.5;
  180. p = 0.5;
  181. qsn = 0.674471117502844;
  182. psn = 0.0002731513884140924;
  183. dsn = 0.00437241570403263;
  184. check(loc, sc, sh, cumulants, std::make_pair(p,qsn), x, dsn, psn);
  185. /* R:
  186. > sn.cumulants(0,1,1e5)
  187. [1] 0.7978845607629713 0.3633802276960805 0.2180136141122883 0.1147706820312645
  188. > qsn(0.5,0,1,1e5)
  189. [1] 0.6744897501960818
  190. > psn(-0.5, 0,1,1e5)
  191. [1] 0
  192. > dsn(-0.5, 0,1,1e5)
  193. [1] 0
  194. */
  195. // 6th
  196. loc = 0; sc = 1; sh = 1e5;
  197. std::cout << "location: " << loc << "\tscale: " << sc << "\tshape: " << sh << std::endl;
  198. cumulants[0] = 0.7978845607629713;
  199. cumulants[1] = 0.3633802276960805;
  200. cumulants[2] = 0.2180136141122883;
  201. cumulants[3] = 0.1147706820312645;
  202. x = -0.5;
  203. p = 0.5;
  204. qsn = 0.6744897501960818;
  205. psn = 0.;
  206. dsn = 0.;
  207. check(loc, sc, sh, cumulants, std::make_pair(p,qsn), x, dsn, psn);
  208. return 0;
  209. }
  210. // EOF