pystatistics 3.3.0__tar.gz → 3.4.0__tar.gz

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (588) hide show
  1. pystatistics-3.4.0/.release/UNRELEASED.md +29 -0
  2. {pystatistics-3.3.0 → pystatistics-3.4.0}/CHANGELOG.md +18 -0
  3. {pystatistics-3.3.0 → pystatistics-3.4.0}/PKG-INFO +13 -2
  4. {pystatistics-3.3.0 → pystatistics-3.4.0}/README.md +12 -1
  5. {pystatistics-3.3.0 → pystatistics-3.4.0}/pyproject.toml +1 -1
  6. {pystatistics-3.3.0 → pystatistics-3.4.0}/pystatistics/__init__.py +1 -1
  7. pystatistics-3.4.0/pystatistics/mice/backends/_gpu_linreg.py +138 -0
  8. pystatistics-3.4.0/pystatistics/mice/backends/_gpu_methods.py +81 -0
  9. {pystatistics-3.3.0 → pystatistics-3.4.0}/pystatistics/mice/backends/cpu.py +7 -4
  10. pystatistics-3.4.0/pystatistics/mice/backends/gpu.py +170 -0
  11. {pystatistics-3.3.0 → pystatistics-3.4.0}/pystatistics/mice/solvers.py +36 -20
  12. pystatistics-3.4.0/tests/mice/test_gpu.py +146 -0
  13. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/mice/test_mice.py +16 -3
  14. pystatistics-3.3.0/.release/UNRELEASED.md +0 -30
  15. {pystatistics-3.3.0 → pystatistics-3.4.0}/.github/workflows/publish.yml +0 -0
  16. {pystatistics-3.3.0 → pystatistics-3.4.0}/.github/workflows/trigger-docs-rebuild.yml +0 -0
  17. {pystatistics-3.3.0 → pystatistics-3.4.0}/.gitignore +0 -0
  18. {pystatistics-3.3.0 → pystatistics-3.4.0}/.release/CHECKLIST.md +0 -0
  19. {pystatistics-3.3.0 → pystatistics-3.4.0}/.release/release.py +0 -0
  20. {pystatistics-3.3.0 → pystatistics-3.4.0}/CLAUDE.md +0 -0
  21. {pystatistics-3.3.0 → pystatistics-3.4.0}/LICENSE +0 -0
  22. {pystatistics-3.3.0 → pystatistics-3.4.0}/benchmarks/mvnmle_bench.py +0 -0
  23. {pystatistics-3.3.0 → pystatistics-3.4.0}/docs/DESIGN.md +0 -0
  24. {pystatistics-3.3.0 → pystatistics-3.4.0}/docs/Forge.md +0 -0
  25. {pystatistics-3.3.0 → pystatistics-3.4.0}/docs/GPU_BACKEND_NOTES.md +0 -0
  26. {pystatistics-3.3.0 → pystatistics-3.4.0}/docs/Makefile +0 -0
  27. {pystatistics-3.3.0 → pystatistics-3.4.0}/docs/PYSTATSBIO_CONTEXT.md +0 -0
  28. {pystatistics-3.3.0 → pystatistics-3.4.0}/docs/ROADMAP.md +0 -0
  29. {pystatistics-3.3.0 → pystatistics-3.4.0}/docs/_static/custom.css +0 -0
  30. {pystatistics-3.3.0 → pystatistics-3.4.0}/docs/anova.rst +0 -0
  31. {pystatistics-3.3.0 → pystatistics-3.4.0}/docs/conf.py +0 -0
  32. {pystatistics-3.3.0 → pystatistics-3.4.0}/docs/core.rst +0 -0
  33. {pystatistics-3.3.0 → pystatistics-3.4.0}/docs/descriptive.rst +0 -0
  34. {pystatistics-3.3.0 → pystatistics-3.4.0}/docs/gam.rst +0 -0
  35. {pystatistics-3.3.0 → pystatistics-3.4.0}/docs/hypothesis.rst +0 -0
  36. {pystatistics-3.3.0 → pystatistics-3.4.0}/docs/index.rst +0 -0
  37. {pystatistics-3.3.0 → pystatistics-3.4.0}/docs/mixed.rst +0 -0
  38. {pystatistics-3.3.0 → pystatistics-3.4.0}/docs/montecarlo.rst +0 -0
  39. {pystatistics-3.3.0 → pystatistics-3.4.0}/docs/multinomial.rst +0 -0
  40. {pystatistics-3.3.0 → pystatistics-3.4.0}/docs/multivariate.rst +0 -0
  41. {pystatistics-3.3.0 → pystatistics-3.4.0}/docs/mvnmle.rst +0 -0
  42. {pystatistics-3.3.0 → pystatistics-3.4.0}/docs/ordinal.rst +0 -0
  43. {pystatistics-3.3.0 → pystatistics-3.4.0}/docs/regression.rst +0 -0
  44. {pystatistics-3.3.0 → pystatistics-3.4.0}/docs/survival.rst +0 -0
  45. {pystatistics-3.3.0 → pystatistics-3.4.0}/docs/timeseries.rst +0 -0
  46. {pystatistics-3.3.0 → pystatistics-3.4.0}/pystatistics/GPU_BACKEND_CONVENTION.md +0 -0
  47. {pystatistics-3.3.0 → pystatistics-3.4.0}/pystatistics/anova/__init__.py +0 -0
  48. {pystatistics-3.3.0 → pystatistics-3.4.0}/pystatistics/anova/_common.py +0 -0
  49. {pystatistics-3.3.0 → pystatistics-3.4.0}/pystatistics/anova/_contrasts.py +0 -0
  50. {pystatistics-3.3.0 → pystatistics-3.4.0}/pystatistics/anova/_levene.py +0 -0
  51. {pystatistics-3.3.0 → pystatistics-3.4.0}/pystatistics/anova/_posthoc.py +0 -0
  52. {pystatistics-3.3.0 → pystatistics-3.4.0}/pystatistics/anova/_repeated.py +0 -0
  53. {pystatistics-3.3.0 → pystatistics-3.4.0}/pystatistics/anova/_ss.py +0 -0
  54. {pystatistics-3.3.0 → pystatistics-3.4.0}/pystatistics/anova/design.py +0 -0
  55. {pystatistics-3.3.0 → pystatistics-3.4.0}/pystatistics/anova/solution.py +0 -0
  56. {pystatistics-3.3.0 → pystatistics-3.4.0}/pystatistics/anova/solvers.py +0 -0
  57. {pystatistics-3.3.0 → pystatistics-3.4.0}/pystatistics/core/__init__.py +0 -0
  58. {pystatistics-3.3.0 → pystatistics-3.4.0}/pystatistics/core/capabilities.py +0 -0
  59. {pystatistics-3.3.0 → pystatistics-3.4.0}/pystatistics/core/compute/__init__.py +0 -0
  60. {pystatistics-3.3.0 → pystatistics-3.4.0}/pystatistics/core/compute/device.py +0 -0
  61. {pystatistics-3.3.0 → pystatistics-3.4.0}/pystatistics/core/compute/linalg/__init__.py +0 -0
  62. {pystatistics-3.3.0 → pystatistics-3.4.0}/pystatistics/core/compute/linalg/batched.py +0 -0
  63. {pystatistics-3.3.0 → pystatistics-3.4.0}/pystatistics/core/compute/linalg/cholesky.py +0 -0
  64. {pystatistics-3.3.0 → pystatistics-3.4.0}/pystatistics/core/compute/linalg/determinant.py +0 -0
  65. {pystatistics-3.3.0 → pystatistics-3.4.0}/pystatistics/core/compute/linalg/qr.py +0 -0
  66. {pystatistics-3.3.0 → pystatistics-3.4.0}/pystatistics/core/compute/linalg/solve.py +0 -0
  67. {pystatistics-3.3.0 → pystatistics-3.4.0}/pystatistics/core/compute/linalg/svd.py +0 -0
  68. {pystatistics-3.3.0 → pystatistics-3.4.0}/pystatistics/core/compute/optimization/__init__.py +0 -0
  69. {pystatistics-3.3.0 → pystatistics-3.4.0}/pystatistics/core/compute/optimization/convergence.py +0 -0
  70. {pystatistics-3.3.0 → pystatistics-3.4.0}/pystatistics/core/compute/precision.py +0 -0
  71. {pystatistics-3.3.0 → pystatistics-3.4.0}/pystatistics/core/compute/timing.py +0 -0
  72. {pystatistics-3.3.0 → pystatistics-3.4.0}/pystatistics/core/compute/tolerances.py +0 -0
  73. {pystatistics-3.3.0 → pystatistics-3.4.0}/pystatistics/core/compute/torch_interop.py +0 -0
  74. {pystatistics-3.3.0 → pystatistics-3.4.0}/pystatistics/core/datasource.py +0 -0
  75. {pystatistics-3.3.0 → pystatistics-3.4.0}/pystatistics/core/encoding.py +0 -0
  76. {pystatistics-3.3.0 → pystatistics-3.4.0}/pystatistics/core/exceptions.py +0 -0
  77. {pystatistics-3.3.0 → pystatistics-3.4.0}/pystatistics/core/protocols.py +0 -0
  78. {pystatistics-3.3.0 → pystatistics-3.4.0}/pystatistics/core/result.py +0 -0
  79. {pystatistics-3.3.0 → pystatistics-3.4.0}/pystatistics/core/validation.py +0 -0
  80. {pystatistics-3.3.0 → pystatistics-3.4.0}/pystatistics/descriptive/__init__.py +0 -0
  81. {pystatistics-3.3.0 → pystatistics-3.4.0}/pystatistics/descriptive/_missing.py +0 -0
  82. {pystatistics-3.3.0 → pystatistics-3.4.0}/pystatistics/descriptive/_quantile_types.py +0 -0
  83. {pystatistics-3.3.0 → pystatistics-3.4.0}/pystatistics/descriptive/backends/__init__.py +0 -0
  84. {pystatistics-3.3.0 → pystatistics-3.4.0}/pystatistics/descriptive/backends/cpu.py +0 -0
  85. {pystatistics-3.3.0 → pystatistics-3.4.0}/pystatistics/descriptive/backends/gpu.py +0 -0
  86. {pystatistics-3.3.0 → pystatistics-3.4.0}/pystatistics/descriptive/design.py +0 -0
  87. {pystatistics-3.3.0 → pystatistics-3.4.0}/pystatistics/descriptive/solution.py +0 -0
  88. {pystatistics-3.3.0 → pystatistics-3.4.0}/pystatistics/descriptive/solvers.py +0 -0
  89. {pystatistics-3.3.0 → pystatistics-3.4.0}/pystatistics/gam/__init__.py +0 -0
  90. {pystatistics-3.3.0 → pystatistics-3.4.0}/pystatistics/gam/_basis.py +0 -0
  91. {pystatistics-3.3.0 → pystatistics-3.4.0}/pystatistics/gam/_common.py +0 -0
  92. {pystatistics-3.3.0 → pystatistics-3.4.0}/pystatistics/gam/_fit.py +0 -0
  93. {pystatistics-3.3.0 → pystatistics-3.4.0}/pystatistics/gam/_gam.py +0 -0
  94. {pystatistics-3.3.0 → pystatistics-3.4.0}/pystatistics/gam/_gcv.py +0 -0
  95. {pystatistics-3.3.0 → pystatistics-3.4.0}/pystatistics/gam/_smooth.py +0 -0
  96. {pystatistics-3.3.0 → pystatistics-3.4.0}/pystatistics/gam/backends/__init__.py +0 -0
  97. {pystatistics-3.3.0 → pystatistics-3.4.0}/pystatistics/gam/backends/_gpu_family.py +0 -0
  98. {pystatistics-3.3.0 → pystatistics-3.4.0}/pystatistics/gam/backends/gpu_pirls.py +0 -0
  99. {pystatistics-3.3.0 → pystatistics-3.4.0}/pystatistics/gam/solution.py +0 -0
  100. {pystatistics-3.3.0 → pystatistics-3.4.0}/pystatistics/hypothesis/__init__.py +0 -0
  101. {pystatistics-3.3.0 → pystatistics-3.4.0}/pystatistics/hypothesis/_common.py +0 -0
  102. {pystatistics-3.3.0 → pystatistics-3.4.0}/pystatistics/hypothesis/_design_factories.py +0 -0
  103. {pystatistics-3.3.0 → pystatistics-3.4.0}/pystatistics/hypothesis/_p_adjust.py +0 -0
  104. {pystatistics-3.3.0 → pystatistics-3.4.0}/pystatistics/hypothesis/backends/__init__.py +0 -0
  105. {pystatistics-3.3.0 → pystatistics-3.4.0}/pystatistics/hypothesis/backends/_chisq_test.py +0 -0
  106. {pystatistics-3.3.0 → pystatistics-3.4.0}/pystatistics/hypothesis/backends/_fisher_test.py +0 -0
  107. {pystatistics-3.3.0 → pystatistics-3.4.0}/pystatistics/hypothesis/backends/_ks_test.py +0 -0
  108. {pystatistics-3.3.0 → pystatistics-3.4.0}/pystatistics/hypothesis/backends/_prop_test.py +0 -0
  109. {pystatistics-3.3.0 → pystatistics-3.4.0}/pystatistics/hypothesis/backends/_t_test.py +0 -0
  110. {pystatistics-3.3.0 → pystatistics-3.4.0}/pystatistics/hypothesis/backends/_var_test.py +0 -0
  111. {pystatistics-3.3.0 → pystatistics-3.4.0}/pystatistics/hypothesis/backends/_wilcox_test.py +0 -0
  112. {pystatistics-3.3.0 → pystatistics-3.4.0}/pystatistics/hypothesis/backends/cpu.py +0 -0
  113. {pystatistics-3.3.0 → pystatistics-3.4.0}/pystatistics/hypothesis/backends/gpu.py +0 -0
  114. {pystatistics-3.3.0 → pystatistics-3.4.0}/pystatistics/hypothesis/design.py +0 -0
  115. {pystatistics-3.3.0 → pystatistics-3.4.0}/pystatistics/hypothesis/solution.py +0 -0
  116. {pystatistics-3.3.0 → pystatistics-3.4.0}/pystatistics/hypothesis/solvers.py +0 -0
  117. {pystatistics-3.3.0 → pystatistics-3.4.0}/pystatistics/mice/__init__.py +0 -0
  118. {pystatistics-3.3.0 → pystatistics-3.4.0}/pystatistics/mice/_chain.py +0 -0
  119. {pystatistics-3.3.0 → pystatistics-3.4.0}/pystatistics/mice/_rng.py +0 -0
  120. {pystatistics-3.3.0 → pystatistics-3.4.0}/pystatistics/mice/_visit.py +0 -0
  121. {pystatistics-3.3.0 → pystatistics-3.4.0}/pystatistics/mice/backends/__init__.py +0 -0
  122. {pystatistics-3.3.0 → pystatistics-3.4.0}/pystatistics/mice/datasets.py +0 -0
  123. {pystatistics-3.3.0 → pystatistics-3.4.0}/pystatistics/mice/design.py +0 -0
  124. {pystatistics-3.3.0 → pystatistics-3.4.0}/pystatistics/mice/methods/__init__.py +0 -0
  125. {pystatistics-3.3.0 → pystatistics-3.4.0}/pystatistics/mice/methods/_linreg.py +0 -0
  126. {pystatistics-3.3.0 → pystatistics-3.4.0}/pystatistics/mice/methods/base.py +0 -0
  127. {pystatistics-3.3.0 → pystatistics-3.4.0}/pystatistics/mice/methods/norm.py +0 -0
  128. {pystatistics-3.3.0 → pystatistics-3.4.0}/pystatistics/mice/methods/pmm.py +0 -0
  129. {pystatistics-3.3.0 → pystatistics-3.4.0}/pystatistics/mice/methods/registry.py +0 -0
  130. {pystatistics-3.3.0 → pystatistics-3.4.0}/pystatistics/mice/pooling.py +0 -0
  131. {pystatistics-3.3.0 → pystatistics-3.4.0}/pystatistics/mice/solution.py +0 -0
  132. {pystatistics-3.3.0 → pystatistics-3.4.0}/pystatistics/mixed/__init__.py +0 -0
  133. {pystatistics-3.3.0 → pystatistics-3.4.0}/pystatistics/mixed/_common.py +0 -0
  134. {pystatistics-3.3.0 → pystatistics-3.4.0}/pystatistics/mixed/_deviance.py +0 -0
  135. {pystatistics-3.3.0 → pystatistics-3.4.0}/pystatistics/mixed/_pirls.py +0 -0
  136. {pystatistics-3.3.0 → pystatistics-3.4.0}/pystatistics/mixed/_pls.py +0 -0
  137. {pystatistics-3.3.0 → pystatistics-3.4.0}/pystatistics/mixed/_random_effects.py +0 -0
  138. {pystatistics-3.3.0 → pystatistics-3.4.0}/pystatistics/mixed/_satterthwaite.py +0 -0
  139. {pystatistics-3.3.0 → pystatistics-3.4.0}/pystatistics/mixed/design.py +0 -0
  140. {pystatistics-3.3.0 → pystatistics-3.4.0}/pystatistics/mixed/solution.py +0 -0
  141. {pystatistics-3.3.0 → pystatistics-3.4.0}/pystatistics/mixed/solvers.py +0 -0
  142. {pystatistics-3.3.0 → pystatistics-3.4.0}/pystatistics/montecarlo/__init__.py +0 -0
  143. {pystatistics-3.3.0 → pystatistics-3.4.0}/pystatistics/montecarlo/_ci.py +0 -0
  144. {pystatistics-3.3.0 → pystatistics-3.4.0}/pystatistics/montecarlo/_common.py +0 -0
  145. {pystatistics-3.3.0 → pystatistics-3.4.0}/pystatistics/montecarlo/_influence.py +0 -0
  146. {pystatistics-3.3.0 → pystatistics-3.4.0}/pystatistics/montecarlo/backends/__init__.py +0 -0
  147. {pystatistics-3.3.0 → pystatistics-3.4.0}/pystatistics/montecarlo/backends/cpu.py +0 -0
  148. {pystatistics-3.3.0 → pystatistics-3.4.0}/pystatistics/montecarlo/backends/gpu.py +0 -0
  149. {pystatistics-3.3.0 → pystatistics-3.4.0}/pystatistics/montecarlo/design.py +0 -0
  150. {pystatistics-3.3.0 → pystatistics-3.4.0}/pystatistics/montecarlo/solution.py +0 -0
  151. {pystatistics-3.3.0 → pystatistics-3.4.0}/pystatistics/montecarlo/solvers.py +0 -0
  152. {pystatistics-3.3.0 → pystatistics-3.4.0}/pystatistics/multinomial/__init__.py +0 -0
  153. {pystatistics-3.3.0 → pystatistics-3.4.0}/pystatistics/multinomial/_common.py +0 -0
  154. {pystatistics-3.3.0 → pystatistics-3.4.0}/pystatistics/multinomial/_likelihood.py +0 -0
  155. {pystatistics-3.3.0 → pystatistics-3.4.0}/pystatistics/multinomial/_solver.py +0 -0
  156. {pystatistics-3.3.0 → pystatistics-3.4.0}/pystatistics/multinomial/backends/__init__.py +0 -0
  157. {pystatistics-3.3.0 → pystatistics-3.4.0}/pystatistics/multinomial/backends/gpu_likelihood.py +0 -0
  158. {pystatistics-3.3.0 → pystatistics-3.4.0}/pystatistics/multinomial/solution.py +0 -0
  159. {pystatistics-3.3.0 → pystatistics-3.4.0}/pystatistics/multivariate/__init__.py +0 -0
  160. {pystatistics-3.3.0 → pystatistics-3.4.0}/pystatistics/multivariate/_common.py +0 -0
  161. {pystatistics-3.3.0 → pystatistics-3.4.0}/pystatistics/multivariate/_factor.py +0 -0
  162. {pystatistics-3.3.0 → pystatistics-3.4.0}/pystatistics/multivariate/_pca.py +0 -0
  163. {pystatistics-3.3.0 → pystatistics-3.4.0}/pystatistics/multivariate/_rotation.py +0 -0
  164. {pystatistics-3.3.0 → pystatistics-3.4.0}/pystatistics/multivariate/backends/__init__.py +0 -0
  165. {pystatistics-3.3.0 → pystatistics-3.4.0}/pystatistics/multivariate/backends/gpu_pca.py +0 -0
  166. {pystatistics-3.3.0 → pystatistics-3.4.0}/pystatistics/mvnmle/__init__.py +0 -0
  167. {pystatistics-3.3.0 → pystatistics-3.4.0}/pystatistics/mvnmle/_monotone.py +0 -0
  168. {pystatistics-3.3.0 → pystatistics-3.4.0}/pystatistics/mvnmle/_objectives/__init__.py +0 -0
  169. {pystatistics-3.3.0 → pystatistics-3.4.0}/pystatistics/mvnmle/_objectives/base.py +0 -0
  170. {pystatistics-3.3.0 → pystatistics-3.4.0}/pystatistics/mvnmle/_objectives/cpu.py +0 -0
  171. {pystatistics-3.3.0 → pystatistics-3.4.0}/pystatistics/mvnmle/_objectives/gpu_fp32.py +0 -0
  172. {pystatistics-3.3.0 → pystatistics-3.4.0}/pystatistics/mvnmle/_objectives/gpu_fp64.py +0 -0
  173. {pystatistics-3.3.0 → pystatistics-3.4.0}/pystatistics/mvnmle/_objectives/parameterizations.py +0 -0
  174. {pystatistics-3.3.0 → pystatistics-3.4.0}/pystatistics/mvnmle/_utils.py +0 -0
  175. {pystatistics-3.3.0 → pystatistics-3.4.0}/pystatistics/mvnmle/backends/__init__.py +0 -0
  176. {pystatistics-3.3.0 → pystatistics-3.4.0}/pystatistics/mvnmle/backends/_em_batched.py +0 -0
  177. {pystatistics-3.3.0 → pystatistics-3.4.0}/pystatistics/mvnmle/backends/_em_batched_np.py +0 -0
  178. {pystatistics-3.3.0 → pystatistics-3.4.0}/pystatistics/mvnmle/backends/_em_batched_patterns.py +0 -0
  179. {pystatistics-3.3.0 → pystatistics-3.4.0}/pystatistics/mvnmle/backends/_em_batched_torch.py +0 -0
  180. {pystatistics-3.3.0 → pystatistics-3.4.0}/pystatistics/mvnmle/backends/_squarem.py +0 -0
  181. {pystatistics-3.3.0 → pystatistics-3.4.0}/pystatistics/mvnmle/backends/cpu.py +0 -0
  182. {pystatistics-3.3.0 → pystatistics-3.4.0}/pystatistics/mvnmle/backends/em.py +0 -0
  183. {pystatistics-3.3.0 → pystatistics-3.4.0}/pystatistics/mvnmle/backends/gpu.py +0 -0
  184. {pystatistics-3.3.0 → pystatistics-3.4.0}/pystatistics/mvnmle/datasets.py +0 -0
  185. {pystatistics-3.3.0 → pystatistics-3.4.0}/pystatistics/mvnmle/design.py +0 -0
  186. {pystatistics-3.3.0 → pystatistics-3.4.0}/pystatistics/mvnmle/mcar_test.py +0 -0
  187. {pystatistics-3.3.0 → pystatistics-3.4.0}/pystatistics/mvnmle/patterns.py +0 -0
  188. {pystatistics-3.3.0 → pystatistics-3.4.0}/pystatistics/mvnmle/solution.py +0 -0
  189. {pystatistics-3.3.0 → pystatistics-3.4.0}/pystatistics/mvnmle/solvers.py +0 -0
  190. {pystatistics-3.3.0 → pystatistics-3.4.0}/pystatistics/ordinal/__init__.py +0 -0
  191. {pystatistics-3.3.0 → pystatistics-3.4.0}/pystatistics/ordinal/_common.py +0 -0
  192. {pystatistics-3.3.0 → pystatistics-3.4.0}/pystatistics/ordinal/_likelihood.py +0 -0
  193. {pystatistics-3.3.0 → pystatistics-3.4.0}/pystatistics/ordinal/_solver.py +0 -0
  194. {pystatistics-3.3.0 → pystatistics-3.4.0}/pystatistics/ordinal/backends/__init__.py +0 -0
  195. {pystatistics-3.3.0 → pystatistics-3.4.0}/pystatistics/ordinal/backends/gpu_likelihood.py +0 -0
  196. {pystatistics-3.3.0 → pystatistics-3.4.0}/pystatistics/ordinal/solution.py +0 -0
  197. {pystatistics-3.3.0 → pystatistics-3.4.0}/pystatistics/py.typed +0 -0
  198. {pystatistics-3.3.0 → pystatistics-3.4.0}/pystatistics/regression/__init__.py +0 -0
  199. {pystatistics-3.3.0 → pystatistics-3.4.0}/pystatistics/regression/_formatting.py +0 -0
  200. {pystatistics-3.3.0 → pystatistics-3.4.0}/pystatistics/regression/_glm.py +0 -0
  201. {pystatistics-3.3.0 → pystatistics-3.4.0}/pystatistics/regression/_linear.py +0 -0
  202. {pystatistics-3.3.0 → pystatistics-3.4.0}/pystatistics/regression/_nb_theta.py +0 -0
  203. {pystatistics-3.3.0 → pystatistics-3.4.0}/pystatistics/regression/backends/__init__.py +0 -0
  204. {pystatistics-3.3.0 → pystatistics-3.4.0}/pystatistics/regression/backends/cpu.py +0 -0
  205. {pystatistics-3.3.0 → pystatistics-3.4.0}/pystatistics/regression/backends/cpu_glm.py +0 -0
  206. {pystatistics-3.3.0 → pystatistics-3.4.0}/pystatistics/regression/backends/gpu.py +0 -0
  207. {pystatistics-3.3.0 → pystatistics-3.4.0}/pystatistics/regression/backends/gpu_glm.py +0 -0
  208. {pystatistics-3.3.0 → pystatistics-3.4.0}/pystatistics/regression/design.py +0 -0
  209. {pystatistics-3.3.0 → pystatistics-3.4.0}/pystatistics/regression/families.py +0 -0
  210. {pystatistics-3.3.0 → pystatistics-3.4.0}/pystatistics/regression/solution.py +0 -0
  211. {pystatistics-3.3.0 → pystatistics-3.4.0}/pystatistics/regression/solvers.py +0 -0
  212. {pystatistics-3.3.0 → pystatistics-3.4.0}/pystatistics/regression/terms.py +0 -0
  213. {pystatistics-3.3.0 → pystatistics-3.4.0}/pystatistics/survival/__init__.py +0 -0
  214. {pystatistics-3.3.0 → pystatistics-3.4.0}/pystatistics/survival/_common.py +0 -0
  215. {pystatistics-3.3.0 → pystatistics-3.4.0}/pystatistics/survival/_cox.py +0 -0
  216. {pystatistics-3.3.0 → pystatistics-3.4.0}/pystatistics/survival/_discrete.py +0 -0
  217. {pystatistics-3.3.0 → pystatistics-3.4.0}/pystatistics/survival/_km.py +0 -0
  218. {pystatistics-3.3.0 → pystatistics-3.4.0}/pystatistics/survival/_logrank.py +0 -0
  219. {pystatistics-3.3.0 → pystatistics-3.4.0}/pystatistics/survival/backends/__init__.py +0 -0
  220. {pystatistics-3.3.0 → pystatistics-3.4.0}/pystatistics/survival/backends/cpu.py +0 -0
  221. {pystatistics-3.3.0 → pystatistics-3.4.0}/pystatistics/survival/backends/gpu.py +0 -0
  222. {pystatistics-3.3.0 → pystatistics-3.4.0}/pystatistics/survival/design.py +0 -0
  223. {pystatistics-3.3.0 → pystatistics-3.4.0}/pystatistics/survival/solution.py +0 -0
  224. {pystatistics-3.3.0 → pystatistics-3.4.0}/pystatistics/survival/solvers.py +0 -0
  225. {pystatistics-3.3.0 → pystatistics-3.4.0}/pystatistics/timeseries/__init__.py +0 -0
  226. {pystatistics-3.3.0 → pystatistics-3.4.0}/pystatistics/timeseries/_acf.py +0 -0
  227. {pystatistics-3.3.0 → pystatistics-3.4.0}/pystatistics/timeseries/_arima_batch.py +0 -0
  228. {pystatistics-3.3.0 → pystatistics-3.4.0}/pystatistics/timeseries/_arima_factored.py +0 -0
  229. {pystatistics-3.3.0 → pystatistics-3.4.0}/pystatistics/timeseries/_arima_fit.py +0 -0
  230. {pystatistics-3.3.0 → pystatistics-3.4.0}/pystatistics/timeseries/_arima_forecast.py +0 -0
  231. {pystatistics-3.3.0 → pystatistics-3.4.0}/pystatistics/timeseries/_arima_kalman.py +0 -0
  232. {pystatistics-3.3.0 → pystatistics-3.4.0}/pystatistics/timeseries/_arima_likelihood.py +0 -0
  233. {pystatistics-3.3.0 → pystatistics-3.4.0}/pystatistics/timeseries/_arima_order.py +0 -0
  234. {pystatistics-3.3.0 → pystatistics-3.4.0}/pystatistics/timeseries/_common.py +0 -0
  235. {pystatistics-3.3.0 → pystatistics-3.4.0}/pystatistics/timeseries/_decomposition.py +0 -0
  236. {pystatistics-3.3.0 → pystatistics-3.4.0}/pystatistics/timeseries/_differencing.py +0 -0
  237. {pystatistics-3.3.0 → pystatistics-3.4.0}/pystatistics/timeseries/_ets_fit.py +0 -0
  238. {pystatistics-3.3.0 → pystatistics-3.4.0}/pystatistics/timeseries/_ets_forecast.py +0 -0
  239. {pystatistics-3.3.0 → pystatistics-3.4.0}/pystatistics/timeseries/_ets_models.py +0 -0
  240. {pystatistics-3.3.0 → pystatistics-3.4.0}/pystatistics/timeseries/_stationarity.py +0 -0
  241. {pystatistics-3.3.0 → pystatistics-3.4.0}/pystatistics/timeseries/_whittle.py +0 -0
  242. {pystatistics-3.3.0 → pystatistics-3.4.0}/pystatistics/timeseries/backends/__init__.py +0 -0
  243. {pystatistics-3.3.0 → pystatistics-3.4.0}/pystatistics/timeseries/backends/whittle_batch_gpu.py +0 -0
  244. {pystatistics-3.3.0 → pystatistics-3.4.0}/pystatistics/timeseries/backends/whittle_gpu.py +0 -0
  245. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/anova/__init__.py +0 -0
  246. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/anova/conftest.py +0 -0
  247. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/anova/test_contrasts.py +0 -0
  248. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/anova/test_design.py +0 -0
  249. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/anova/test_factorial.py +0 -0
  250. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/anova/test_levene.py +0 -0
  251. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/anova/test_oneway.py +0 -0
  252. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/anova/test_posthoc.py +0 -0
  253. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/anova/test_r_validation.py +0 -0
  254. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/anova/test_repeated_measures.py +0 -0
  255. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/benchmark_gpu.py +0 -0
  256. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/conftest.py +0 -0
  257. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/core/test_datasource.py +0 -0
  258. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/core/test_exceptions.py +0 -0
  259. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/core/test_result.py +0 -0
  260. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/core/test_torch_interop.py +0 -0
  261. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/core/test_validation.py +0 -0
  262. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/descriptive/__init__.py +0 -0
  263. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/descriptive/conftest.py +0 -0
  264. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/descriptive/test_cor.py +0 -0
  265. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/descriptive/test_cov.py +0 -0
  266. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/descriptive/test_describe.py +0 -0
  267. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/descriptive/test_gpu.py +0 -0
  268. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/descriptive/test_missing.py +0 -0
  269. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/descriptive/test_moments.py +0 -0
  270. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/descriptive/test_quantile.py +0 -0
  271. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/descriptive/test_r_validation.py +0 -0
  272. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/fixtures/anova_ancova_meta.json +0 -0
  273. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/fixtures/anova_ancova_r_results.json +0 -0
  274. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/fixtures/anova_bonferroni_meta.json +0 -0
  275. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/fixtures/anova_bonferroni_r_results.json +0 -0
  276. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/fixtures/anova_eta_meta.json +0 -0
  277. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/fixtures/anova_eta_r_results.json +0 -0
  278. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/fixtures/anova_levene_meta.json +0 -0
  279. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/fixtures/anova_levene_r_results.json +0 -0
  280. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/fixtures/anova_oneway_balanced_meta.json +0 -0
  281. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/fixtures/anova_oneway_balanced_r_results.json +0 -0
  282. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/fixtures/anova_oneway_unbalanced_meta.json +0 -0
  283. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/fixtures/anova_oneway_unbalanced_r_results.json +0 -0
  284. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/fixtures/anova_rm_mixed_meta.json +0 -0
  285. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/fixtures/anova_rm_mixed_r_results.json +0 -0
  286. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/fixtures/anova_rm_within_meta.json +0 -0
  287. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/fixtures/anova_rm_within_r_results.json +0 -0
  288. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/fixtures/anova_tukey_meta.json +0 -0
  289. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/fixtures/anova_tukey_r_results.json +0 -0
  290. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/fixtures/anova_twoway_balanced_meta.json +0 -0
  291. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/fixtures/anova_twoway_balanced_r_results.json +0 -0
  292. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/fixtures/anova_twoway_unbalanced_meta.json +0 -0
  293. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/fixtures/anova_twoway_unbalanced_r_results.json +0 -0
  294. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/fixtures/basic_100x3.csv +0 -0
  295. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/fixtures/basic_100x3_meta.json +0 -0
  296. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/fixtures/basic_100x3_r_results.json +0 -0
  297. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/fixtures/collinear_almost.csv +0 -0
  298. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/fixtures/collinear_almost_meta.json +0 -0
  299. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/fixtures/collinear_almost_r_results.json +0 -0
  300. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/fixtures/desc_basic_100x5.csv +0 -0
  301. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/fixtures/desc_basic_100x5_meta.json +0 -0
  302. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/fixtures/desc_basic_100x5_r_results.json +0 -0
  303. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/fixtures/desc_constant_column.csv +0 -0
  304. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/fixtures/desc_constant_column_meta.json +0 -0
  305. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/fixtures/desc_constant_column_r_results.json +0 -0
  306. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/fixtures/desc_extreme_values.csv +0 -0
  307. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/fixtures/desc_extreme_values_meta.json +0 -0
  308. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/fixtures/desc_extreme_values_r_results.json +0 -0
  309. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/fixtures/desc_large_1000x10.csv +0 -0
  310. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/fixtures/desc_large_1000x10_meta.json +0 -0
  311. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/fixtures/desc_large_1000x10_r_results.json +0 -0
  312. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/fixtures/desc_nan_columnwise.csv +0 -0
  313. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/fixtures/desc_nan_columnwise_meta.json +0 -0
  314. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/fixtures/desc_nan_columnwise_r_results.json +0 -0
  315. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/fixtures/desc_nan_scattered.csv +0 -0
  316. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/fixtures/desc_nan_scattered_meta.json +0 -0
  317. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/fixtures/desc_nan_scattered_r_results.json +0 -0
  318. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/fixtures/desc_negative_correlation.csv +0 -0
  319. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/fixtures/desc_negative_correlation_meta.json +0 -0
  320. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/fixtures/desc_negative_correlation_r_results.json +0 -0
  321. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/fixtures/desc_perfect_correlation.csv +0 -0
  322. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/fixtures/desc_perfect_correlation_meta.json +0 -0
  323. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/fixtures/desc_perfect_correlation_r_results.json +0 -0
  324. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/fixtures/desc_single_column.csv +0 -0
  325. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/fixtures/desc_single_column_meta.json +0 -0
  326. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/fixtures/desc_single_column_r_results.json +0 -0
  327. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/fixtures/desc_ties.csv +0 -0
  328. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/fixtures/desc_ties_meta.json +0 -0
  329. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/fixtures/desc_ties_r_results.json +0 -0
  330. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/fixtures/different_scales.csv +0 -0
  331. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/fixtures/different_scales_meta.json +0 -0
  332. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/fixtures/different_scales_r_results.json +0 -0
  333. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/fixtures/generate_anova_fixtures.py +0 -0
  334. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/fixtures/generate_descriptive_fixtures.py +0 -0
  335. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/fixtures/generate_fixtures.py +0 -0
  336. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/fixtures/generate_glm_fixtures.py +0 -0
  337. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/fixtures/generate_hypothesis_fixtures.py +0 -0
  338. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/fixtures/generate_mixed_fixtures.py +0 -0
  339. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/fixtures/generate_montecarlo_fixtures.py +0 -0
  340. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/fixtures/generate_survival_fixtures.py +0 -0
  341. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/fixtures/glm_binomial_balanced.csv +0 -0
  342. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/fixtures/glm_binomial_balanced_meta.json +0 -0
  343. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/fixtures/glm_binomial_balanced_r_results.json +0 -0
  344. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/fixtures/glm_binomial_basic.csv +0 -0
  345. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/fixtures/glm_binomial_basic_meta.json +0 -0
  346. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/fixtures/glm_binomial_basic_r_results.json +0 -0
  347. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/fixtures/glm_binomial_large.csv +0 -0
  348. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/fixtures/glm_binomial_large_meta.json +0 -0
  349. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/fixtures/glm_binomial_large_r_results.json +0 -0
  350. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/fixtures/glm_binomial_separated.csv +0 -0
  351. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/fixtures/glm_binomial_separated_meta.json +0 -0
  352. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/fixtures/glm_binomial_separated_r_results.json +0 -0
  353. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/fixtures/glm_gaussian_basic.csv +0 -0
  354. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/fixtures/glm_gaussian_basic_meta.json +0 -0
  355. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/fixtures/glm_gaussian_basic_r_results.json +0 -0
  356. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/fixtures/glm_gaussian_large.csv +0 -0
  357. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/fixtures/glm_gaussian_large_meta.json +0 -0
  358. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/fixtures/glm_gaussian_large_r_results.json +0 -0
  359. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/fixtures/glm_poisson_basic.csv +0 -0
  360. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/fixtures/glm_poisson_basic_meta.json +0 -0
  361. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/fixtures/glm_poisson_basic_r_results.json +0 -0
  362. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/fixtures/glm_poisson_large_counts.csv +0 -0
  363. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/fixtures/glm_poisson_large_counts_meta.json +0 -0
  364. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/fixtures/glm_poisson_large_counts_r_results.json +0 -0
  365. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/fixtures/glm_poisson_zeros.csv +0 -0
  366. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/fixtures/glm_poisson_zeros_meta.json +0 -0
  367. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/fixtures/glm_poisson_zeros_r_results.json +0 -0
  368. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/fixtures/high_noise.csv +0 -0
  369. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/fixtures/high_noise_meta.json +0 -0
  370. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/fixtures/high_noise_r_results.json +0 -0
  371. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/fixtures/htest_chisq_2x2_yates_meta.json +0 -0
  372. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/fixtures/htest_chisq_2x2_yates_r_results.json +0 -0
  373. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/fixtures/htest_chisq_3x3_meta.json +0 -0
  374. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/fixtures/htest_chisq_3x3_r_results.json +0 -0
  375. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/fixtures/htest_chisq_gof_meta.json +0 -0
  376. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/fixtures/htest_chisq_gof_r_results.json +0 -0
  377. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/fixtures/htest_chisq_gof_unequal_meta.json +0 -0
  378. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/fixtures/htest_chisq_gof_unequal_r_results.json +0 -0
  379. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/fixtures/htest_fisher_2x2_less_meta.json +0 -0
  380. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/fixtures/htest_fisher_2x2_less_r_results.json +0 -0
  381. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/fixtures/htest_fisher_2x2_meta.json +0 -0
  382. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/fixtures/htest_fisher_2x2_r_results.json +0 -0
  383. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/fixtures/htest_fisher_3x3_meta.json +0 -0
  384. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/fixtures/htest_fisher_3x3_r_results.json +0 -0
  385. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/fixtures/htest_ks_onesample_norm_meta.json +0 -0
  386. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/fixtures/htest_ks_onesample_norm_r_results.json +0 -0
  387. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/fixtures/htest_ks_twosample_meta.json +0 -0
  388. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/fixtures/htest_ks_twosample_r_results.json +0 -0
  389. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/fixtures/htest_prop_onesample_meta.json +0 -0
  390. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/fixtures/htest_prop_onesample_r_results.json +0 -0
  391. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/fixtures/htest_prop_twosample_meta.json +0 -0
  392. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/fixtures/htest_prop_twosample_r_results.json +0 -0
  393. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/fixtures/htest_t_onesample_meta.json +0 -0
  394. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/fixtures/htest_t_onesample_r_results.json +0 -0
  395. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/fixtures/htest_t_paired_meta.json +0 -0
  396. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/fixtures/htest_t_paired_r_results.json +0 -0
  397. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/fixtures/htest_t_pooled_meta.json +0 -0
  398. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/fixtures/htest_t_pooled_r_results.json +0 -0
  399. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/fixtures/htest_t_welch_meta.json +0 -0
  400. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/fixtures/htest_t_welch_r_results.json +0 -0
  401. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/fixtures/htest_var_basic_meta.json +0 -0
  402. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/fixtures/htest_var_basic_r_results.json +0 -0
  403. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/fixtures/htest_wilcox_ranksum_meta.json +0 -0
  404. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/fixtures/htest_wilcox_ranksum_r_results.json +0 -0
  405. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/fixtures/htest_wilcox_signed_meta.json +0 -0
  406. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/fixtures/htest_wilcox_signed_r_results.json +0 -0
  407. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/fixtures/ill_conditioned.csv +0 -0
  408. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/fixtures/ill_conditioned_meta.json +0 -0
  409. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/fixtures/ill_conditioned_r_results.json +0 -0
  410. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/fixtures/large_coeffs.csv +0 -0
  411. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/fixtures/large_coeffs_meta.json +0 -0
  412. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/fixtures/large_coeffs_r_results.json +0 -0
  413. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/fixtures/mc_boot_ci_90_meta.json +0 -0
  414. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/fixtures/mc_boot_ci_90_r_results.json +0 -0
  415. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/fixtures/mc_boot_ci_normal_meta.json +0 -0
  416. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/fixtures/mc_boot_ci_normal_r_results.json +0 -0
  417. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/fixtures/mc_boot_ci_skewed_meta.json +0 -0
  418. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/fixtures/mc_boot_ci_skewed_r_results.json +0 -0
  419. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/fixtures/mc_boot_mean_balanced_meta.json +0 -0
  420. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/fixtures/mc_boot_mean_balanced_r_results.json +0 -0
  421. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/fixtures/mc_boot_mean_ordinary_meta.json +0 -0
  422. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/fixtures/mc_boot_mean_ordinary_r_results.json +0 -0
  423. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/fixtures/mc_boot_median_meta.json +0 -0
  424. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/fixtures/mc_boot_median_r_results.json +0 -0
  425. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/fixtures/mc_boot_variance_meta.json +0 -0
  426. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/fixtures/mc_boot_variance_r_results.json +0 -0
  427. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/fixtures/mc_perm_greater_meta.json +0 -0
  428. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/fixtures/mc_perm_greater_r_results.json +0 -0
  429. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/fixtures/mc_perm_not_significant_meta.json +0 -0
  430. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/fixtures/mc_perm_not_significant_r_results.json +0 -0
  431. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/fixtures/mc_perm_significant_meta.json +0 -0
  432. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/fixtures/mc_perm_significant_r_results.json +0 -0
  433. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/fixtures/mixed/glmm_binomial.csv +0 -0
  434. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/fixtures/mixed/glmm_poisson.csv +0 -0
  435. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/fixtures/mixed/lmm_crossed.csv +0 -0
  436. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/fixtures/mixed/lmm_intercept.csv +0 -0
  437. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/fixtures/mixed/lmm_ml.csv +0 -0
  438. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/fixtures/mixed/lmm_no_effect.csv +0 -0
  439. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/fixtures/mixed/lmm_slope.csv +0 -0
  440. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/fixtures/mixed/mixed_meta.json +0 -0
  441. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/fixtures/mixed/mixed_r_results.json +0 -0
  442. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/fixtures/near_square.csv +0 -0
  443. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/fixtures/near_square_meta.json +0 -0
  444. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/fixtures/near_square_r_results.json +0 -0
  445. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/fixtures/no_intercept.csv +0 -0
  446. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/fixtures/no_intercept_meta.json +0 -0
  447. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/fixtures/no_intercept_r_results.json +0 -0
  448. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/fixtures/run_r_anova_validation.R +0 -0
  449. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/fixtures/run_r_descriptive_validation.R +0 -0
  450. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/fixtures/run_r_glm_validation.R +0 -0
  451. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/fixtures/run_r_hypothesis_validation.R +0 -0
  452. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/fixtures/run_r_mixed_validation.R +0 -0
  453. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/fixtures/run_r_montecarlo_validation.R +0 -0
  454. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/fixtures/run_r_survival_validation.R +0 -0
  455. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/fixtures/run_r_validation.R +0 -0
  456. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/fixtures/run_validation.sh +0 -0
  457. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/fixtures/small_noise.csv +0 -0
  458. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/fixtures/small_noise_meta.json +0 -0
  459. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/fixtures/small_noise_r_results.json +0 -0
  460. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/fixtures/surv_cox_breslow_meta.json +0 -0
  461. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/fixtures/surv_cox_breslow_r_results.json +0 -0
  462. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/fixtures/surv_cox_single_meta.json +0 -0
  463. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/fixtures/surv_cox_single_r_results.json +0 -0
  464. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/fixtures/surv_cox_ties_meta.json +0 -0
  465. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/fixtures/surv_cox_ties_r_results.json +0 -0
  466. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/fixtures/surv_cox_two_cov_meta.json +0 -0
  467. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/fixtures/surv_cox_two_cov_r_results.json +0 -0
  468. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/fixtures/surv_km_basic_meta.json +0 -0
  469. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/fixtures/surv_km_basic_r_results.json +0 -0
  470. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/fixtures/surv_km_heavy_cens_meta.json +0 -0
  471. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/fixtures/surv_km_heavy_cens_r_results.json +0 -0
  472. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/fixtures/surv_km_loglog_ci_meta.json +0 -0
  473. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/fixtures/surv_km_loglog_ci_r_results.json +0 -0
  474. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/fixtures/surv_km_no_cens_meta.json +0 -0
  475. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/fixtures/surv_km_no_cens_r_results.json +0 -0
  476. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/fixtures/surv_km_plain_ci_meta.json +0 -0
  477. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/fixtures/surv_km_plain_ci_r_results.json +0 -0
  478. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/fixtures/surv_km_ties_meta.json +0 -0
  479. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/fixtures/surv_km_ties_r_results.json +0 -0
  480. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/fixtures/surv_lr_peto_meta.json +0 -0
  481. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/fixtures/surv_lr_peto_r_results.json +0 -0
  482. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/fixtures/surv_lr_three_group_meta.json +0 -0
  483. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/fixtures/surv_lr_three_group_r_results.json +0 -0
  484. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/fixtures/surv_lr_two_group_meta.json +0 -0
  485. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/fixtures/surv_lr_two_group_r_results.json +0 -0
  486. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/fixtures/tall_skinny.csv +0 -0
  487. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/fixtures/tall_skinny_meta.json +0 -0
  488. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/fixtures/tall_skinny_r_results.json +0 -0
  489. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/fixtures/validate_against_r.py +0 -0
  490. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/gam/__init__.py +0 -0
  491. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/gam/test_gam.py +0 -0
  492. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/hypothesis/__init__.py +0 -0
  493. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/hypothesis/conftest.py +0 -0
  494. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/hypothesis/test_chisq_test.py +0 -0
  495. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/hypothesis/test_design_split.py +0 -0
  496. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/hypothesis/test_fisher_test.py +0 -0
  497. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/hypothesis/test_gpu.py +0 -0
  498. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/hypothesis/test_ks_test.py +0 -0
  499. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/hypothesis/test_p_adjust.py +0 -0
  500. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/hypothesis/test_prop_test.py +0 -0
  501. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/hypothesis/test_r_validation.py +0 -0
  502. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/hypothesis/test_t_test.py +0 -0
  503. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/hypothesis/test_var_test.py +0 -0
  504. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/hypothesis/test_wilcox_test.py +0 -0
  505. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/mice/__init__.py +0 -0
  506. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/mice/references/generate_mice_fixtures.R +0 -0
  507. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/mice/references/mice_reference.json +0 -0
  508. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/mice/references/mice_validation_complete.csv +0 -0
  509. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/mice/references/mice_validation_data.csv +0 -0
  510. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/mice/test_datasets.py +0 -0
  511. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/mice/test_design.py +0 -0
  512. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/mice/test_methods.py +0 -0
  513. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/mice/test_pooling.py +0 -0
  514. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/mice/test_r_validation.py +0 -0
  515. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/mice/test_rng.py +0 -0
  516. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/mice/test_visit.py +0 -0
  517. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/mixed/__init__.py +0 -0
  518. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/mixed/conftest.py +0 -0
  519. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/mixed/test_glmm.py +0 -0
  520. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/mixed/test_lmm_crossed.py +0 -0
  521. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/mixed/test_lmm_intercept.py +0 -0
  522. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/mixed/test_lmm_nested.py +0 -0
  523. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/mixed/test_lmm_slope.py +0 -0
  524. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/mixed/test_pls.py +0 -0
  525. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/mixed/test_r_validation.py +0 -0
  526. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/mixed/test_random_effects.py +0 -0
  527. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/mixed/test_satterthwaite.py +0 -0
  528. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/montecarlo/__init__.py +0 -0
  529. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/montecarlo/conftest.py +0 -0
  530. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/montecarlo/test_batched_solver.py +0 -0
  531. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/montecarlo/test_boot_ci.py +0 -0
  532. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/montecarlo/test_bootstrap.py +0 -0
  533. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/montecarlo/test_gpu.py +0 -0
  534. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/montecarlo/test_influence.py +0 -0
  535. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/montecarlo/test_permutation.py +0 -0
  536. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/montecarlo/test_r_validation.py +0 -0
  537. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/multinomial/__init__.py +0 -0
  538. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/multinomial/test_multinom.py +0 -0
  539. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/multivariate/__init__.py +0 -0
  540. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/multivariate/test_multivariate.py +0 -0
  541. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/mvnmle/references/apple_em_reference.json +0 -0
  542. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/mvnmle/references/apple_reference.json +0 -0
  543. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/mvnmle/references/generate_em_fixtures.R +0 -0
  544. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/mvnmle/references/little_mcar_apple.json +0 -0
  545. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/mvnmle/references/little_mcar_complete.json +0 -0
  546. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/mvnmle/references/little_mcar_extreme.json +0 -0
  547. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/mvnmle/references/little_mcar_missvals.json +0 -0
  548. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/mvnmle/references/little_mcar_simple_mcar.json +0 -0
  549. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/mvnmle/references/little_mcar_summary.json +0 -0
  550. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/mvnmle/references/missvals_em_reference.json +0 -0
  551. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/mvnmle/references/missvals_reference.json +0 -0
  552. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/mvnmle/references/small_test_reference.json +0 -0
  553. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/mvnmle/test_em.py +0 -0
  554. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/mvnmle/test_gpu.py +0 -0
  555. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/mvnmle/test_mcar.py +0 -0
  556. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/mvnmle/test_mlest.py +0 -0
  557. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/mvnmle/test_monotone.py +0 -0
  558. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/mvnmle/test_no_silent_fallback.py +0 -0
  559. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/mvnmle/test_squarem.py +0 -0
  560. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/ordinal/__init__.py +0 -0
  561. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/ordinal/test_ordinal.py +0 -0
  562. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/regression/benchmark.py +0 -0
  563. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/regression/benchmark.r +0 -0
  564. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/regression/conftest.py +0 -0
  565. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/regression/test_fit.py +0 -0
  566. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/regression/test_gamma_nb.py +0 -0
  567. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/regression/test_glm.py +0 -0
  568. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/regression/test_glm_gpu.py +0 -0
  569. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/regression/test_glm_r_validation.py +0 -0
  570. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/regression/test_module_split.py +0 -0
  571. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/regression/test_r_validation.py +0 -0
  572. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/regression/test_stress_gpu.py +0 -0
  573. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/regression/test_terms.py +0 -0
  574. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/regression/test_terms_gpu.py +0 -0
  575. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/survival/__init__.py +0 -0
  576. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/survival/conftest.py +0 -0
  577. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/survival/test_coxph.py +0 -0
  578. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/survival/test_discrete_time.py +0 -0
  579. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/survival/test_gpu.py +0 -0
  580. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/survival/test_kaplan_meier.py +0 -0
  581. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/survival/test_logrank.py +0 -0
  582. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/survival/test_r_validation.py +0 -0
  583. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/test_code_quality.py +0 -0
  584. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/timeseries/__init__.py +0 -0
  585. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/timeseries/test_acf_stationarity.py +0 -0
  586. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/timeseries/test_arima.py +0 -0
  587. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/timeseries/test_decomposition.py +0 -0
  588. {pystatistics-3.3.0 → pystatistics-3.4.0}/tests/timeseries/test_ets.py +0 -0
@@ -0,0 +1,29 @@
1
+ # Unreleased Changes
2
+
3
+ > This file tracks all changes since the last stable release.
4
+ > Updated by whoever makes a change, on whatever machine.
5
+ > Synced via git so all sessions (Mac, Linux, etc.) see the same state.
6
+ >
7
+ > When ready to release, run: `python .release/release.py --status`
8
+ > and follow the manual release flow in the script docstring.
9
+
10
+ ## Changes
11
+
12
+ - GPU backend for `mice` (CUDA). `mice(..., backend='gpu')` runs the `m`
13
+ imputation chains batched on the GPU as the leading tensor dimension: each
14
+ sweep step is a batched Bayesian linear solve (`torch.linalg.solve` + batched
15
+ Cholesky) and, for PMM, a batched nearest-neighbour donor search
16
+ (`(m, n_mis, n_obs)` distances → `topk`). `backend='auto'` selects CUDA when
17
+ available, else CPU (never MPS, matching the other modules). New `use_fp64`
18
+ argument runs the GPU path in double precision on CUDA (default FP32).
19
+ - GPU results match the CPU reference distributionally at the GPU/FP32 tolerance
20
+ tier (PMM donor copies are exact in FP64, exact-to-FP32 otherwise). Validated
21
+ in `tests/mice/test_gpu.py` against the CPU path rather than R directly.
22
+ - Measured PMM speedups vs the CPU backend on an RTX 5070 Ti: ~39× at n=1000
23
+ (p=8, m=20, maxit=8) and ~135× at n=3000 (p=10, m=20, maxit=8); the gain grows
24
+ with n because the donor search dominates and batches well on the GPU.
25
+ - Internal: the MICE backend contract now takes a `seed` (each backend spawns
26
+ its own RNG streams) instead of pre-spawned streams, so the CPU and GPU
27
+ backends share one `run()` signature. No public API change.
28
+ - MPS (Apple Silicon) is not yet validated for MICE; `backend='gpu'` raises a
29
+ clear error on MPS rather than running unverified. CUDA is supported.
@@ -1,5 +1,23 @@
1
1
  # Changelog
2
2
 
3
+ ## 3.4.0
4
+
5
+ GPU acceleration for MICE.
6
+
7
+ - **`mice(..., backend='gpu')` runs on CUDA GPUs.** The `m` imputation chains
8
+ run together on the GPU, with the per-variable linear solves and the
9
+ predictive-mean-matching donor search batched across chains. `backend='auto'`
10
+ uses a CUDA GPU when one is available and falls back to the CPU otherwise.
11
+ - **Large speedups on bigger problems.** Because the donor search dominates and
12
+ parallelises well, the GPU advantage grows with sample size — for example,
13
+ predictive mean matching was roughly 39× faster at n=1000 and 135× faster at
14
+ n=3000 than the CPU backend on an RTX 5070 Ti (m=20, maxit=8). GPU results
15
+ match the CPU backend at the standard GPU/FP32 tolerance.
16
+ - **`use_fp64=True`** runs the GPU path in double precision on CUDA for closer
17
+ agreement with the CPU reference (default is FP32, the fast path).
18
+ - GPU acceleration requires a CUDA GPU; Apple Silicon (MPS) is not yet supported
19
+ for MICE and is refused with a clear message rather than run unverified.
20
+
3
21
  ## 3.3.0
4
22
 
5
23
  Multiple imputation by chained equations (MICE) for multivariate missing data.
@@ -1,6 +1,6 @@
1
1
  Metadata-Version: 2.4
2
2
  Name: pystatistics
3
- Version: 3.3.0
3
+ Version: 3.4.0
4
4
  Summary: GPU-accelerated statistical computing for Python
5
5
  Project-URL: Homepage, https://sgcx.org/technology/pystatistics/
6
6
  Project-URL: Documentation, https://sgcx.org/docs/pystatistics/
@@ -86,7 +86,7 @@ PyStatistics maintains two parallel computational paths with distinct goals:
86
86
  | `multivariate/` | Complete | PCA and maximum likelihood factor analysis with varimax/promax rotation |
87
87
  | `timeseries/` | Complete | ACF, PACF, ADF, KPSS, ETS, ARIMA, SARIMA, auto_arima, decompose, STL |
88
88
  | `gam/` | Complete | Generalized additive models with penalized regression splines matching R mgcv::gam |
89
- | `mice/` | Numeric (CPU) | Multiple imputation by chained equations: PMM and Bayesian linear regression, Rubin's-rules pooling, validated against R mice |
89
+ | `mice/` | Numeric | Multiple imputation by chained equations: PMM and Bayesian linear regression, Rubin's-rules pooling, validated against R mice; CUDA GPU backend |
90
90
 
91
91
  See [docs/ROADMAP.md](docs/ROADMAP.md) for detailed scope, GPU applicability, and implementation priority for each module.
92
92
 
@@ -413,6 +413,17 @@ pip install pystatistics[dev]
413
413
 
414
414
  ## What's New
415
415
 
416
+ ### 3.4.0 — GPU acceleration for MICE
417
+
418
+ - `mice(..., backend='gpu')` runs the imputation chains on a CUDA GPU, batching
419
+ the per-variable solves and the predictive-mean-matching donor search across
420
+ chains. `backend='auto'` uses a CUDA GPU when available, else the CPU.
421
+ - The speedup grows with sample size (the donor search dominates and batches
422
+ well): predictive mean matching ran ~39× faster at n=1000 and ~135× faster at
423
+ n=3000 than the CPU backend on an RTX 5070 Ti. GPU results match the CPU
424
+ backend at the GPU/FP32 tolerance; pass `use_fp64=True` for double precision.
425
+ - Requires a CUDA GPU; Apple Silicon (MPS) is not yet supported for MICE.
426
+
416
427
  ### 3.3.0 — Multiple imputation (MICE)
417
428
 
418
429
  - New `mice` module: multiple imputation by chained equations for numeric data
@@ -39,7 +39,7 @@ PyStatistics maintains two parallel computational paths with distinct goals:
39
39
  | `multivariate/` | Complete | PCA and maximum likelihood factor analysis with varimax/promax rotation |
40
40
  | `timeseries/` | Complete | ACF, PACF, ADF, KPSS, ETS, ARIMA, SARIMA, auto_arima, decompose, STL |
41
41
  | `gam/` | Complete | Generalized additive models with penalized regression splines matching R mgcv::gam |
42
- | `mice/` | Numeric (CPU) | Multiple imputation by chained equations: PMM and Bayesian linear regression, Rubin's-rules pooling, validated against R mice |
42
+ | `mice/` | Numeric | Multiple imputation by chained equations: PMM and Bayesian linear regression, Rubin's-rules pooling, validated against R mice; CUDA GPU backend |
43
43
 
44
44
  See [docs/ROADMAP.md](docs/ROADMAP.md) for detailed scope, GPU applicability, and implementation priority for each module.
45
45
 
@@ -366,6 +366,17 @@ pip install pystatistics[dev]
366
366
 
367
367
  ## What's New
368
368
 
369
+ ### 3.4.0 — GPU acceleration for MICE
370
+
371
+ - `mice(..., backend='gpu')` runs the imputation chains on a CUDA GPU, batching
372
+ the per-variable solves and the predictive-mean-matching donor search across
373
+ chains. `backend='auto'` uses a CUDA GPU when available, else the CPU.
374
+ - The speedup grows with sample size (the donor search dominates and batches
375
+ well): predictive mean matching ran ~39× faster at n=1000 and ~135× faster at
376
+ n=3000 than the CPU backend on an RTX 5070 Ti. GPU results match the CPU
377
+ backend at the GPU/FP32 tolerance; pass `use_fp64=True` for double precision.
378
+ - Requires a CUDA GPU; Apple Silicon (MPS) is not yet supported for MICE.
379
+
369
380
  ### 3.3.0 — Multiple imputation (MICE)
370
381
 
371
382
  - New `mice` module: multiple imputation by chained equations for numeric data
@@ -4,7 +4,7 @@ build-backend = "hatchling.build"
4
4
 
5
5
  [project]
6
6
  name = "pystatistics"
7
- version = "3.3.0"
7
+ version = "3.4.0"
8
8
  description = "GPU-accelerated statistical computing for Python"
9
9
  readme = "README.md"
10
10
  license = "MIT"
@@ -16,7 +16,7 @@ Usage:
16
16
  result = fit(design)
17
17
  """
18
18
 
19
- __version__ = "3.3.0"
19
+ __version__ = "3.4.0"
20
20
  __author__ = "Hai-Shuo"
21
21
  __email__ = "contact@sgcx.org"
22
22
 
@@ -0,0 +1,138 @@
1
+ """
2
+ Batched Bayesian linear-regression posterior draw on the GPU.
3
+
4
+ This is the GPU counterpart of ``methods/_linreg.py``: the same Bayesian draw,
5
+ but vectorized over the ``m`` imputation chains as the leading batch dimension.
6
+ At a given sweep step every chain is fitting the *same* target column on the
7
+ *same* observed rows, but with different predictor values (each chain imputed
8
+ the other columns differently), so we solve ``m`` independent linear systems at
9
+ once with batched cuBLAS/cuSOLVER kernels.
10
+
11
+ Posterior draw (identical model to the CPU path):
12
+
13
+ beta_hat = (X'X + ridge)^{-1} X'y batched solve
14
+ df = max(n_obs - n_params, 1) integer, shared by chains
15
+ sigma* = sqrt( RSS / chi2(df) ) chi2 = sum of df squared N(0,1)
16
+ beta* = beta_hat + sigma* * L z L L' = (X'X + ridge)^{-1}
17
+
18
+ The chi-square is built from standard normals (``df`` is a non-negative integer)
19
+ so the only randomness source is the seeded ``torch.Generator`` — no reliance on
20
+ ``torch.distributions``, which ignores explicit generators.
21
+
22
+ All randomness flows through the passed generator (CLAUDE.md Rule 6). Results
23
+ match the CPU reference distributionally, at the GPU/FP32 tolerance tier — not
24
+ bit-for-bit (different RNG, single precision).
25
+ """
26
+
27
+ from __future__ import annotations
28
+
29
+ from dataclasses import dataclass
30
+
31
+ # Matches the CPU ridge (methods/_linreg.py) — a tiny relative penalty keeping
32
+ # the batched Gram matrices invertible under FP32.
33
+ _DEFAULT_RIDGE = 1e-5
34
+
35
+
36
+ @dataclass
37
+ class BatchedLinRegDraw:
38
+ """Batched point estimate + posterior draw (leading dim = m chains)."""
39
+
40
+ beta_hat: "object" # (m, q+1) tensor
41
+ beta_draw: "object" # (m, q+1) tensor
42
+ sigma_draw: "object" # (m,) tensor
43
+
44
+
45
+ def add_intercept(X):
46
+ """Prepend a ones column to a batched predictor tensor (m, n, q) -> (m,n,q+1)."""
47
+ import torch
48
+
49
+ m, n, _ = X.shape
50
+ ones = torch.ones((m, n, 1), dtype=X.dtype, device=X.device)
51
+ return torch.cat([ones, X], dim=2)
52
+
53
+
54
+ def batched_bayes_linreg_draw(
55
+ y_obs,
56
+ X_obs,
57
+ gen,
58
+ ridge: float = _DEFAULT_RIDGE,
59
+ ) -> BatchedLinRegDraw:
60
+ """Draw once from the Gaussian linear-model posterior for every chain.
61
+
62
+ Parameters
63
+ ----------
64
+ y_obs : (m, n_obs) tensor
65
+ Observed responses (identical across chains, batched for uniform ops).
66
+ X_obs : (m, n_obs, q) tensor
67
+ Observed predictors WITHOUT an intercept column (added internally).
68
+ gen : torch.Generator
69
+ Sole randomness source, on the same device as the tensors.
70
+ ridge : float
71
+ Relative ridge penalty on the diagonal of X'X.
72
+ """
73
+ import torch
74
+
75
+ Xa = add_intercept(X_obs) # (m, n_obs, q+1)
76
+ m, n_obs, n_params = Xa.shape
77
+ dtype, device = Xa.dtype, Xa.device
78
+
79
+ Xt = Xa.transpose(1, 2) # (m, q+1, n_obs)
80
+ XtX = Xt @ Xa # (m, q+1, q+1)
81
+
82
+ diag = torch.diagonal(XtX, dim1=1, dim2=2) # (m, q+1)
83
+ diag_mean = diag.mean(dim=1).clamp_min(torch.finfo(dtype).tiny) # (m,)
84
+ eye = torch.eye(n_params, dtype=dtype, device=device)
85
+ XtX_ridge = XtX + ridge * diag_mean[:, None, None] * eye
86
+
87
+ Xty = Xt @ y_obs.unsqueeze(-1) # (m, q+1, 1)
88
+ beta_hat = torch.linalg.solve(XtX_ridge, Xty).squeeze(-1) # (m, q+1)
89
+
90
+ resid = y_obs - (Xa @ beta_hat.unsqueeze(-1)).squeeze(-1) # (m, n_obs)
91
+ rss = (resid * resid).sum(dim=1) # (m,)
92
+ df = max(n_obs - n_params, 1)
93
+
94
+ # chi2(df) = sum of df squared standard normals (df is an integer).
95
+ z_chi = torch.randn((m, df), generator=gen, dtype=dtype, device=device)
96
+ chi = (z_chi * z_chi).sum(dim=1).clamp_min(torch.finfo(dtype).tiny) # (m,)
97
+ sigma_draw = torch.where(
98
+ rss > 0, torch.sqrt(rss / chi), torch.zeros_like(rss)
99
+ ) # (m,)
100
+
101
+ V = torch.linalg.inv(XtX_ridge) # (m, q+1, q+1)
102
+ L = _batched_safe_cholesky(V) # (m, q+1, q+1), L L' = V
103
+ z_beta = torch.randn((m, n_params), generator=gen, dtype=dtype, device=device)
104
+ beta_draw = beta_hat + sigma_draw[:, None] * (L @ z_beta.unsqueeze(-1)).squeeze(-1)
105
+
106
+ return BatchedLinRegDraw(
107
+ beta_hat=beta_hat, beta_draw=beta_draw, sigma_draw=sigma_draw
108
+ )
109
+
110
+
111
+ def _batched_safe_cholesky(V):
112
+ """Lower Cholesky of each (symmetric PSD) matrix in a batch, with jitter.
113
+
114
+ ``V`` is a batch of inverse-Gram matrices — positive definite in exact
115
+ arithmetic, but FP32 rounding can leave one marginally indefinite. We
116
+ symmetrize and add escalating jitter to the *whole batch* (cheap, keeps the
117
+ op batched) until ``cholesky_ex`` reports success for every matrix.
118
+ """
119
+ import torch
120
+
121
+ Vs = 0.5 * (V + V.transpose(1, 2))
122
+ eye = torch.eye(Vs.shape[1], dtype=Vs.dtype, device=Vs.device)
123
+ diag = torch.diagonal(Vs, dim1=1, dim2=2)
124
+ scale = diag.mean().clamp_min(1.0).item()
125
+
126
+ jitter = 0.0
127
+ for _ in range(8):
128
+ M = Vs if jitter == 0.0 else Vs + jitter * eye
129
+ L, info = torch.linalg.cholesky_ex(M)
130
+ if not torch.any(info):
131
+ return L
132
+ jitter = scale * (1e-8 if jitter == 0.0 else 10.0 * jitter)
133
+
134
+ # Documented last resort (Rule 1): eigenvalue-clipped PSD factor. Reached
135
+ # only if a matrix is badly degenerate despite ridge + jitter.
136
+ w, Q = torch.linalg.eigh(Vs)
137
+ w = w.clamp_min(0.0)
138
+ return Q @ torch.diag_embed(torch.sqrt(w))
@@ -0,0 +1,81 @@
1
+ """
2
+ Batched GPU imputation methods: ``norm`` and ``pmm``.
3
+
4
+ These mirror ``methods/norm.py`` and ``methods/pmm.py`` but operate on tensors
5
+ batched over the ``m`` chains. Each takes the observed/missing predictor blocks
6
+ for one target column across all chains and returns the imputed values for every
7
+ chain at once, so a whole sweep step is a handful of batched kernels.
8
+
9
+ The GPU backend dispatches to these by method name; a name with no GPU
10
+ implementation is refused by the backend (fail loud, Rule 1) rather than
11
+ silently downgraded.
12
+ """
13
+
14
+ from __future__ import annotations
15
+
16
+ from pystatistics.mice.backends._gpu_linreg import (
17
+ add_intercept,
18
+ batched_bayes_linreg_draw,
19
+ )
20
+
21
+
22
+ def gpu_norm_impute(y_obs, X_obs, X_mis, gen, *, donors=None):
23
+ """Batched Bayesian linear-regression imputation (R ``norm``).
24
+
25
+ Parameters mirror the CPU method but are batched: ``y_obs`` (m, n_obs),
26
+ ``X_obs`` (m, n_obs, q), ``X_mis`` (m, n_mis, q). Returns (m, n_mis).
27
+ ``donors`` is accepted and ignored so the backend can call every method
28
+ with one uniform signature.
29
+ """
30
+ import torch
31
+
32
+ draw = batched_bayes_linreg_draw(y_obs, X_obs, gen)
33
+ Xa_mis = add_intercept(X_mis)
34
+ yhat_mis = (Xa_mis @ draw.beta_draw.unsqueeze(-1)).squeeze(-1) # (m, n_mis)
35
+ noise = torch.randn(
36
+ yhat_mis.shape, generator=gen, dtype=yhat_mis.dtype, device=yhat_mis.device
37
+ )
38
+ return yhat_mis + draw.sigma_draw[:, None] * noise
39
+
40
+
41
+ def gpu_pmm_impute(y_obs, X_obs, X_mis, gen, *, donors=5):
42
+ """Batched predictive mean matching (R ``pmm``, matchtype=1).
43
+
44
+ Observed fitted values use ``beta_hat``; missing fitted values use the
45
+ posterior draw ``beta*``. For each missing row in each chain, pick one of
46
+ the ``k`` nearest observed fitted values at random and copy that observed
47
+ value. Returns (m, n_mis).
48
+ """
49
+ import torch
50
+
51
+ draw = batched_bayes_linreg_draw(y_obs, X_obs, gen)
52
+ Xa_obs = add_intercept(X_obs)
53
+ Xa_mis = add_intercept(X_mis)
54
+ yhat_obs = (Xa_obs @ draw.beta_hat.unsqueeze(-1)).squeeze(-1) # (m, n_obs)
55
+ yhat_mis = (Xa_mis @ draw.beta_draw.unsqueeze(-1)).squeeze(-1) # (m, n_mis)
56
+
57
+ m, n_obs = yhat_obs.shape
58
+ n_mis = yhat_mis.shape[1]
59
+ k = min(donors, n_obs)
60
+
61
+ # |yhat_mis - yhat_obs| for every (chain, missing row, observed row).
62
+ dist = (yhat_mis[:, :, None] - yhat_obs[:, None, :]).abs() # (m, n_mis, n_obs)
63
+ # k nearest observed fitted values (indices into n_obs).
64
+ _, cand = torch.topk(dist, k, dim=2, largest=False) # (m, n_mis, k)
65
+
66
+ # One random donor per (chain, missing row) among its k candidates.
67
+ pick = torch.randint(
68
+ 0, k, (m, n_mis), generator=gen, device=yhat_obs.device
69
+ ) # (m, n_mis)
70
+ donor_idx = torch.gather(cand, 2, pick.unsqueeze(-1)).squeeze(-1) # (m, n_mis)
71
+
72
+ # Copy the observed donor values (gather along the observed-row axis).
73
+ return torch.gather(y_obs, 1, donor_idx) # (m, n_mis)
74
+
75
+
76
+ # Method-name -> batched implementation. The backend translates the design's
77
+ # per-column method name through this table; unknown names are refused there.
78
+ GPU_METHODS = {
79
+ "norm": gpu_norm_impute,
80
+ "pmm": gpu_pmm_impute,
81
+ }
@@ -17,6 +17,7 @@ import numpy as np
17
17
  from pystatistics.core.compute.timing import Timer
18
18
  from pystatistics.core.result import Result
19
19
  from pystatistics.mice._chain import run_chain
20
+ from pystatistics.mice._rng import spawn_streams
20
21
  from pystatistics.mice.design import MICEDesign
21
22
  from pystatistics.mice.solution import MICEParams
22
23
 
@@ -35,7 +36,7 @@ class CPUMiceBackend:
35
36
  m: int,
36
37
  maxit: int,
37
38
  visit_sequence: tuple[int, ...],
38
- streams: list[np.random.Generator],
39
+ seed: int,
39
40
  ) -> Result[MICEParams]:
40
41
  """Run ``m`` chains and package the imputations.
41
42
 
@@ -48,13 +49,15 @@ class CPUMiceBackend:
48
49
  Iterations per chain.
49
50
  visit_sequence : tuple of int
50
51
  Column visit order within each iteration.
51
- streams : list of numpy.random.Generator
52
- One independent RNG per chain; ``len(streams) == m`` (the solver
53
- guarantees this).
52
+ seed : int
53
+ Master RNG seed. The backend spawns one independent, reproducible
54
+ stream per chain from it.
54
55
  """
55
56
  timer = Timer()
56
57
  timer.start()
57
58
 
59
+ streams = spawn_streams(seed, m)
60
+
58
61
  completed = np.empty((m, design.n, design.p), dtype=np.float64)
59
62
  chain_means = np.empty((m, maxit, len(design.incomplete_columns)))
60
63
  chain_vars = np.empty((m, maxit, len(design.incomplete_columns)))
@@ -0,0 +1,170 @@
1
+ """
2
+ GPU backend for MICE.
3
+
4
+ Implements the same ``run`` entrypoint as the CPU backend, but runs all ``m``
5
+ imputation chains concurrently on a CUDA GPU with the chain index as the leading
6
+ tensor batch dimension. Each sweep step — visit column ``j``, fit its method on
7
+ the observed rows, overwrite its missing cells — becomes a handful of batched
8
+ kernels across the ``m`` chains (batched linear solves + Cholesky, and for PMM a
9
+ batched nearest-neighbour donor search).
10
+
11
+ Why batch over chains: the ``m`` chains are statistically independent and share
12
+ the missingness pattern, so they have identical shapes at every step — an ideal
13
+ batch. The sweep stays sequential *within* a chain (column ``j`` depends on the
14
+ columns imputed before it), which is inherent to chained equations.
15
+
16
+ Validation tier: GPU results match the CPU reference distributionally at the
17
+ ``GPU_FP32`` tolerance, not bit-for-bit (FP32 + a different RNG). FP64 is
18
+ available on CUDA (``use_fp64=True``) for closer parity.
19
+
20
+ Determinism: a single seeded ``torch.Generator`` on the device is the only
21
+ randomness source. Given the same seed and device, a run reproduces its own
22
+ output to within FP32 kernel non-determinism.
23
+ """
24
+
25
+ from __future__ import annotations
26
+
27
+ from pystatistics.core.compute.timing import Timer
28
+ from pystatistics.core.compute.torch_interop import to_host_f64
29
+ from pystatistics.core.exceptions import ValidationError
30
+ from pystatistics.core.result import Result
31
+ from pystatistics.mice.backends._gpu_methods import GPU_METHODS
32
+ from pystatistics.mice.design import MICEDesign
33
+ from pystatistics.mice.solution import MICEParams
34
+
35
+ # R mice default donor count for PMM (the design does not carry a per-column
36
+ # donor count, so the GPU path uses the same default as the CPU PMMMethod).
37
+ _PMM_DONORS = 5
38
+
39
+
40
+ class GPUMiceBackend:
41
+ """Runs MICE chains batched on a CUDA GPU."""
42
+
43
+ def __init__(self, device: str = "cuda", use_fp64: bool = False):
44
+ self.device = device
45
+ self.use_fp64 = use_fp64
46
+
47
+ @property
48
+ def name(self) -> str:
49
+ return f"gpu_{'fp64' if self.use_fp64 else 'fp32'}"
50
+
51
+ def run(
52
+ self,
53
+ design: MICEDesign,
54
+ *,
55
+ m: int,
56
+ maxit: int,
57
+ visit_sequence: tuple[int, ...],
58
+ seed: int,
59
+ ) -> Result[MICEParams]:
60
+ import torch
61
+
62
+ # Validate that every incomplete column's method has a GPU kernel before
63
+ # touching the device (fail loud at the boundary, Rule 2).
64
+ for j in design.incomplete_columns:
65
+ meth = design.method_for(j)
66
+ if meth not in GPU_METHODS:
67
+ raise ValidationError(
68
+ f"Method {meth!r} (column {j}) has no GPU implementation. "
69
+ f"GPU methods: {sorted(GPU_METHODS)}. Use backend='cpu'."
70
+ )
71
+
72
+ timer = Timer()
73
+ timer.start()
74
+
75
+ dtype = torch.float64 if self.use_fp64 else torch.float32
76
+ dev = torch.device(self.device)
77
+ gen = torch.Generator(device=dev)
78
+ gen.manual_seed(int(seed))
79
+
80
+ n, p = design.n, design.p
81
+ incomplete = design.incomplete_columns
82
+ incomplete_pos = {j: k for k, j in enumerate(incomplete)}
83
+
84
+ with timer.section("transfer"):
85
+ base = torch.as_tensor(design.data, device=dev, dtype=dtype) # (n, p)
86
+ mask = torch.as_tensor(design.missing_mask, device=dev) # (n, p)
87
+ # m independent copies of the data (chains diverge after init).
88
+ data = base.unsqueeze(0).repeat(m, 1, 1) # (m, n, p)
89
+
90
+ # Precompute per-incomplete-column index tensors (shared by all chains).
91
+ obs_idx, mis_idx, pred_idx = {}, {}, {}
92
+ for j in incomplete:
93
+ mcol = mask[:, j]
94
+ obs_idx[j] = torch.nonzero(~mcol, as_tuple=False).squeeze(1)
95
+ mis_idx[j] = torch.nonzero(mcol, as_tuple=False).squeeze(1)
96
+ pred_idx[j] = torch.tensor(
97
+ [c for c in range(p) if c != j], device=dev, dtype=torch.long
98
+ )
99
+
100
+ with timer.section("init"):
101
+ self._initialise(data, base, obs_idx, mis_idx, incomplete, m, gen, dev)
102
+
103
+ chain_mean = torch.empty((m, maxit, len(incomplete)), dtype=dtype, device=dev)
104
+ chain_var = torch.empty((m, maxit, len(incomplete)), dtype=dtype, device=dev)
105
+
106
+ with timer.section("sweep"):
107
+ for it in range(maxit):
108
+ for j in visit_sequence:
109
+ method_fn = GPU_METHODS[design.method_for(j)]
110
+ X = data[:, :, pred_idx[j]] # (m, n, q)
111
+ X_obs = X[:, obs_idx[j], :] # (m, n_obs, q)
112
+ X_mis = X[:, mis_idx[j], :] # (m, n_mis, q)
113
+ y_obs = data[:, obs_idx[j], j] # (m, n_obs)
114
+
115
+ imputed = method_fn(
116
+ y_obs, X_obs, X_mis, gen, donors=_PMM_DONORS
117
+ )
118
+ data[:, mis_idx[j], j] = imputed
119
+
120
+ for j in incomplete:
121
+ cells = data[:, mis_idx[j], j] # (m, n_mis)
122
+ k = incomplete_pos[j]
123
+ chain_mean[:, it, k] = cells.mean(dim=1)
124
+ chain_var[:, it, k] = cells.var(dim=1, unbiased=False)
125
+
126
+ with timer.section("download"):
127
+ completed = to_host_f64(data)
128
+ chain_mean_host = to_host_f64(chain_mean)
129
+ chain_var_host = to_host_f64(chain_var)
130
+
131
+ timer.stop()
132
+
133
+ params = MICEParams(
134
+ completed=completed,
135
+ chain_mean=chain_mean_host,
136
+ chain_var=chain_var_host,
137
+ incomplete_columns=incomplete,
138
+ m=m,
139
+ maxit=maxit,
140
+ visit_sequence=visit_sequence,
141
+ )
142
+ return Result(
143
+ params=params,
144
+ info={
145
+ "method": "chained_equations",
146
+ "m": m,
147
+ "maxit": maxit,
148
+ "device": self.device,
149
+ "precision": "fp64" if self.use_fp64 else "fp32",
150
+ "visit_sequence": list(visit_sequence),
151
+ },
152
+ timing=timer.result(),
153
+ backend_name=self.name,
154
+ warnings=(),
155
+ )
156
+
157
+ @staticmethod
158
+ def _initialise(data, base, obs_idx, mis_idx, incomplete, m, gen, dev):
159
+ """Fill missing cells by sampling observed values of the same column,
160
+ independently per chain. Mutates ``data`` in place."""
161
+ import torch
162
+
163
+ for j in incomplete:
164
+ observed = base[obs_idx[j], j] # (n_obs,)
165
+ n_obs = observed.shape[0]
166
+ n_mis = mis_idx[j].shape[0]
167
+ draw_idx = torch.randint(
168
+ 0, n_obs, (m, n_mis), generator=gen, device=dev
169
+ )
170
+ data[:, mis_idx[j], j] = observed[draw_idx]
@@ -20,7 +20,6 @@ import warnings
20
20
  from typing import Literal, Mapping, Sequence
21
21
 
22
22
  from pystatistics.core.compute.device import select_device
23
- from pystatistics.mice._rng import spawn_streams
24
23
  from pystatistics.mice._visit import resolve_visit_sequence
25
24
  from pystatistics.mice.design import MICEDesign
26
25
  from pystatistics.mice.solution import MICESolution
@@ -38,6 +37,7 @@ def mice(
38
37
  methods: Mapping | Sequence[str] | None = None,
39
38
  visit_sequence: Sequence[int] | None = None,
40
39
  backend: BackendChoice | None = None,
40
+ use_fp64: bool = False,
41
41
  verbose: bool = False,
42
42
  ) -> MICESolution:
43
43
  """Multiple imputation by chained equations (numeric columns, CPU).
@@ -64,8 +64,14 @@ def mice(
64
64
  Column visit order within each iteration. Defaults to incomplete
65
65
  columns in ascending index order (R "roman" default).
66
66
  backend : {'cpu', 'gpu', 'auto'} or None
67
- Compute backend. Default None -> 'cpu'. GPU is not implemented in this
68
- release; requesting it raises.
67
+ Compute backend. Default None -> 'cpu' (the R-validated reference path).
68
+ 'gpu' runs the chains batched on a CUDA GPU; 'auto' uses CUDA when
69
+ available, else CPU. GPU results match the CPU backend at the GPU/FP32
70
+ tolerance tier.
71
+ use_fp64 : bool
72
+ Only relevant on the GPU. Run the GPU chains in double precision (CUDA
73
+ only) for closer parity with the CPU reference. Default False (FP32,
74
+ the fast consumer-GPU path). Ignored on CPU (always double precision).
69
75
  verbose : bool
70
76
  Print progress information.
71
77
 
@@ -105,8 +111,7 @@ def mice(
105
111
  )
106
112
 
107
113
  visit = resolve_visit_sequence(design.incomplete_columns, visit_sequence)
108
- backend_impl = _get_backend(backend)
109
- streams = spawn_streams(seed, m)
114
+ backend_impl = _get_backend(backend, use_fp64)
110
115
 
111
116
  if verbose:
112
117
  print(
@@ -116,7 +121,7 @@ def mice(
116
121
  )
117
122
 
118
123
  result = backend_impl.run(
119
- design, m=m, maxit=maxit, visit_sequence=visit, streams=streams
124
+ design, m=m, maxit=maxit, visit_sequence=visit, seed=seed
120
125
  )
121
126
 
122
127
  if verbose:
@@ -125,30 +130,41 @@ def mice(
125
130
  return MICESolution(_result=result, _design=design)
126
131
 
127
132
 
128
- def _get_backend(choice: BackendChoice | None):
129
- """Resolve the compute backend. None -> CPU; GPU not yet implemented."""
133
+ def _get_backend(choice: BackendChoice | None, use_fp64: bool):
134
+ """Resolve the compute backend.
135
+
136
+ None/'cpu' -> CPU. 'gpu' -> CUDA GPU (raises on MPS, which is not yet
137
+ validated for MICE). 'auto' -> CUDA when available, else CPU; like the
138
+ other pystatistics modules, 'auto' never selects MPS.
139
+ """
130
140
  if choice is None or choice == "cpu":
131
141
  from pystatistics.mice.backends.cpu import CPUMiceBackend
132
142
 
133
143
  return CPUMiceBackend()
134
144
 
135
145
  if choice == "auto":
136
- # 'auto' currently means CPU: no GPU backend ships in this release.
137
- # Kept as an accepted value so callers and the Stage-2 GPU path share
138
- # one vocabulary.
146
+ device = select_device("auto")
147
+ if device.device_type == "cuda":
148
+ from pystatistics.mice.backends.gpu import GPUMiceBackend
149
+
150
+ return GPUMiceBackend(device="cuda", use_fp64=use_fp64)
151
+ # CPU, or MPS (never auto-selected): use the CPU reference path.
139
152
  from pystatistics.mice.backends.cpu import CPUMiceBackend
140
153
 
141
154
  return CPUMiceBackend()
142
155
 
143
156
  if choice == "gpu":
144
- # Fail loud rather than silently downgrading (Rule 1). select_device
145
- # gives a precise hardware error if no GPU exists; otherwise we still
146
- # refuse because the GPU chain backend is Stage 2.
147
- select_device("gpu")
148
- raise NotImplementedError(
149
- "backend='gpu' is not available in this release. MICE ships a "
150
- "validated CPU implementation first; GPU acceleration is planned. "
151
- "Use backend='cpu' (the default)."
152
- )
157
+ device = select_device("gpu") # raises RuntimeError if no GPU
158
+ if device.device_type == "mps":
159
+ raise NotImplementedError(
160
+ "backend='gpu' for MICE is validated on CUDA only in this "
161
+ "release. The chained-equations sweep has not been validated "
162
+ "on Apple Silicon (MPS), so it is refused rather than run "
163
+ "unverified. Use backend='cpu' (the default) on a Mac; CUDA "
164
+ "GPUs are supported."
165
+ )
166
+ from pystatistics.mice.backends.gpu import GPUMiceBackend
167
+
168
+ return GPUMiceBackend(device=device.device_type, use_fp64=use_fp64)
153
169
 
154
170
  raise ValueError(f"Unknown backend: {choice!r}")