scipy 1.15.3__cp312-cp312-musllinux_1_2_aarch64.whl → 1.16.0rc2__cp312-cp312-musllinux_1_2_aarch64.whl

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 (641) hide show
  1. scipy/__config__.py +10 -10
  2. scipy/__init__.py +3 -6
  3. scipy/_cyutility.cpython-312-aarch64-linux-musl.so +0 -0
  4. scipy/_lib/_array_api.py +486 -161
  5. scipy/_lib/_array_api_compat_vendor.py +9 -0
  6. scipy/_lib/_bunch.py +4 -0
  7. scipy/_lib/_ccallback_c.cpython-312-aarch64-linux-musl.so +0 -0
  8. scipy/_lib/_docscrape.py +1 -1
  9. scipy/_lib/_elementwise_iterative_method.py +15 -26
  10. scipy/_lib/_fpumode.cpython-312-aarch64-linux-musl.so +0 -0
  11. scipy/_lib/_sparse.py +41 -0
  12. scipy/_lib/_test_ccallback.cpython-312-aarch64-linux-musl.so +0 -0
  13. scipy/_lib/_test_deprecation_call.cpython-312-aarch64-linux-musl.so +0 -0
  14. scipy/_lib/_test_deprecation_def.cpython-312-aarch64-linux-musl.so +0 -0
  15. scipy/_lib/_testutils.py +6 -2
  16. scipy/_lib/_uarray/_uarray.cpython-312-aarch64-linux-musl.so +0 -0
  17. scipy/_lib/_util.py +222 -125
  18. scipy/_lib/array_api_compat/__init__.py +4 -4
  19. scipy/_lib/array_api_compat/_internal.py +19 -6
  20. scipy/_lib/array_api_compat/common/__init__.py +1 -1
  21. scipy/_lib/array_api_compat/common/_aliases.py +365 -193
  22. scipy/_lib/array_api_compat/common/_fft.py +94 -64
  23. scipy/_lib/array_api_compat/common/_helpers.py +413 -180
  24. scipy/_lib/array_api_compat/common/_linalg.py +116 -40
  25. scipy/_lib/array_api_compat/common/_typing.py +179 -10
  26. scipy/_lib/array_api_compat/cupy/__init__.py +1 -4
  27. scipy/_lib/array_api_compat/cupy/_aliases.py +61 -41
  28. scipy/_lib/array_api_compat/cupy/_info.py +16 -6
  29. scipy/_lib/array_api_compat/cupy/_typing.py +24 -39
  30. scipy/_lib/array_api_compat/dask/array/__init__.py +6 -3
  31. scipy/_lib/array_api_compat/dask/array/_aliases.py +267 -108
  32. scipy/_lib/array_api_compat/dask/array/_info.py +105 -34
  33. scipy/_lib/array_api_compat/dask/array/fft.py +5 -8
  34. scipy/_lib/array_api_compat/dask/array/linalg.py +21 -22
  35. scipy/_lib/array_api_compat/numpy/__init__.py +13 -15
  36. scipy/_lib/array_api_compat/numpy/_aliases.py +98 -49
  37. scipy/_lib/array_api_compat/numpy/_info.py +36 -16
  38. scipy/_lib/array_api_compat/numpy/_typing.py +27 -43
  39. scipy/_lib/array_api_compat/numpy/fft.py +11 -5
  40. scipy/_lib/array_api_compat/numpy/linalg.py +75 -22
  41. scipy/_lib/array_api_compat/torch/__init__.py +3 -5
  42. scipy/_lib/array_api_compat/torch/_aliases.py +262 -159
  43. scipy/_lib/array_api_compat/torch/_info.py +27 -16
  44. scipy/_lib/array_api_compat/torch/_typing.py +3 -0
  45. scipy/_lib/array_api_compat/torch/fft.py +17 -18
  46. scipy/_lib/array_api_compat/torch/linalg.py +16 -16
  47. scipy/_lib/array_api_extra/__init__.py +26 -3
  48. scipy/_lib/array_api_extra/_delegation.py +171 -0
  49. scipy/_lib/array_api_extra/_lib/__init__.py +1 -0
  50. scipy/_lib/array_api_extra/_lib/_at.py +463 -0
  51. scipy/_lib/array_api_extra/_lib/_backends.py +46 -0
  52. scipy/_lib/array_api_extra/_lib/_funcs.py +937 -0
  53. scipy/_lib/array_api_extra/_lib/_lazy.py +357 -0
  54. scipy/_lib/array_api_extra/_lib/_testing.py +278 -0
  55. scipy/_lib/array_api_extra/_lib/_utils/__init__.py +1 -0
  56. scipy/_lib/array_api_extra/_lib/_utils/_compat.py +74 -0
  57. scipy/_lib/array_api_extra/_lib/_utils/_compat.pyi +45 -0
  58. scipy/_lib/array_api_extra/_lib/_utils/_helpers.py +559 -0
  59. scipy/_lib/array_api_extra/_lib/_utils/_typing.py +10 -0
  60. scipy/_lib/array_api_extra/_lib/_utils/_typing.pyi +105 -0
  61. scipy/_lib/array_api_extra/testing.py +359 -0
  62. scipy/_lib/decorator.py +2 -2
  63. scipy/_lib/doccer.py +1 -7
  64. scipy/_lib/messagestream.cpython-312-aarch64-linux-musl.so +0 -0
  65. scipy/_lib/pyprima/__init__.py +212 -0
  66. scipy/_lib/pyprima/cobyla/__init__.py +0 -0
  67. scipy/_lib/pyprima/cobyla/cobyla.py +559 -0
  68. scipy/_lib/pyprima/cobyla/cobylb.py +714 -0
  69. scipy/_lib/pyprima/cobyla/geometry.py +226 -0
  70. scipy/_lib/pyprima/cobyla/initialize.py +215 -0
  71. scipy/_lib/pyprima/cobyla/trustregion.py +492 -0
  72. scipy/_lib/pyprima/cobyla/update.py +289 -0
  73. scipy/_lib/pyprima/common/__init__.py +0 -0
  74. scipy/_lib/pyprima/common/_bounds.py +34 -0
  75. scipy/_lib/pyprima/common/_linear_constraints.py +46 -0
  76. scipy/_lib/pyprima/common/_nonlinear_constraints.py +54 -0
  77. scipy/_lib/pyprima/common/_project.py +173 -0
  78. scipy/_lib/pyprima/common/checkbreak.py +93 -0
  79. scipy/_lib/pyprima/common/consts.py +47 -0
  80. scipy/_lib/pyprima/common/evaluate.py +99 -0
  81. scipy/_lib/pyprima/common/history.py +38 -0
  82. scipy/_lib/pyprima/common/infos.py +30 -0
  83. scipy/_lib/pyprima/common/linalg.py +435 -0
  84. scipy/_lib/pyprima/common/message.py +290 -0
  85. scipy/_lib/pyprima/common/powalg.py +131 -0
  86. scipy/_lib/pyprima/common/preproc.py +277 -0
  87. scipy/_lib/pyprima/common/present.py +5 -0
  88. scipy/_lib/pyprima/common/ratio.py +54 -0
  89. scipy/_lib/pyprima/common/redrho.py +47 -0
  90. scipy/_lib/pyprima/common/selectx.py +296 -0
  91. scipy/_lib/tests/test__util.py +105 -121
  92. scipy/_lib/tests/test_array_api.py +166 -35
  93. scipy/_lib/tests/test_bunch.py +7 -0
  94. scipy/_lib/tests/test_ccallback.py +2 -10
  95. scipy/_lib/tests/test_public_api.py +13 -0
  96. scipy/cluster/_hierarchy.cpython-312-aarch64-linux-musl.so +0 -0
  97. scipy/cluster/_optimal_leaf_ordering.cpython-312-aarch64-linux-musl.so +0 -0
  98. scipy/cluster/_vq.cpython-312-aarch64-linux-musl.so +0 -0
  99. scipy/cluster/hierarchy.py +393 -223
  100. scipy/cluster/tests/test_hierarchy.py +273 -335
  101. scipy/cluster/tests/test_vq.py +45 -61
  102. scipy/cluster/vq.py +39 -35
  103. scipy/conftest.py +263 -157
  104. scipy/constants/_constants.py +4 -1
  105. scipy/constants/tests/test_codata.py +2 -2
  106. scipy/constants/tests/test_constants.py +11 -18
  107. scipy/datasets/_download_all.py +15 -1
  108. scipy/datasets/_fetchers.py +7 -1
  109. scipy/datasets/_utils.py +1 -1
  110. scipy/differentiate/_differentiate.py +25 -25
  111. scipy/differentiate/tests/test_differentiate.py +24 -25
  112. scipy/fft/_basic.py +20 -0
  113. scipy/fft/_helper.py +3 -34
  114. scipy/fft/_pocketfft/helper.py +29 -1
  115. scipy/fft/_pocketfft/pypocketfft.cpython-312-aarch64-linux-musl.so +0 -0
  116. scipy/fft/_pocketfft/tests/test_basic.py +2 -4
  117. scipy/fft/_pocketfft/tests/test_real_transforms.py +4 -4
  118. scipy/fft/_realtransforms.py +13 -0
  119. scipy/fft/tests/test_basic.py +27 -25
  120. scipy/fft/tests/test_fftlog.py +16 -7
  121. scipy/fft/tests/test_helper.py +18 -34
  122. scipy/fft/tests/test_real_transforms.py +8 -10
  123. scipy/fftpack/convolve.cpython-312-aarch64-linux-musl.so +0 -0
  124. scipy/fftpack/tests/test_basic.py +2 -4
  125. scipy/fftpack/tests/test_real_transforms.py +8 -9
  126. scipy/integrate/_bvp.py +9 -3
  127. scipy/integrate/_cubature.py +3 -2
  128. scipy/integrate/_dop.cpython-312-aarch64-linux-musl.so +0 -0
  129. scipy/integrate/_lsoda.cpython-312-aarch64-linux-musl.so +0 -0
  130. scipy/integrate/_ode.py +9 -2
  131. scipy/integrate/_odepack.cpython-312-aarch64-linux-musl.so +0 -0
  132. scipy/integrate/_quad_vec.py +21 -29
  133. scipy/integrate/_quadpack.cpython-312-aarch64-linux-musl.so +0 -0
  134. scipy/integrate/_quadpack_py.py +11 -7
  135. scipy/integrate/_quadrature.py +3 -3
  136. scipy/integrate/_rules/_base.py +2 -2
  137. scipy/integrate/_tanhsinh.py +48 -47
  138. scipy/integrate/_test_multivariate.cpython-312-aarch64-linux-musl.so +0 -0
  139. scipy/integrate/_test_odeint_banded.cpython-312-aarch64-linux-musl.so +0 -0
  140. scipy/integrate/_vode.cpython-312-aarch64-linux-musl.so +0 -0
  141. scipy/integrate/tests/test__quad_vec.py +0 -6
  142. scipy/integrate/tests/test_banded_ode_solvers.py +85 -0
  143. scipy/integrate/tests/test_cubature.py +21 -35
  144. scipy/integrate/tests/test_quadrature.py +6 -8
  145. scipy/integrate/tests/test_tanhsinh.py +56 -48
  146. scipy/interpolate/__init__.py +70 -58
  147. scipy/interpolate/_bary_rational.py +22 -22
  148. scipy/interpolate/_bsplines.py +119 -66
  149. scipy/interpolate/_cubic.py +65 -50
  150. scipy/interpolate/_dfitpack.cpython-312-aarch64-linux-musl.so +0 -0
  151. scipy/interpolate/_dierckx.cpython-312-aarch64-linux-musl.so +0 -0
  152. scipy/interpolate/_fitpack.cpython-312-aarch64-linux-musl.so +0 -0
  153. scipy/interpolate/_fitpack2.py +9 -6
  154. scipy/interpolate/_fitpack_impl.py +32 -26
  155. scipy/interpolate/_fitpack_repro.py +23 -19
  156. scipy/interpolate/_interpnd.cpython-312-aarch64-linux-musl.so +0 -0
  157. scipy/interpolate/_interpolate.py +30 -12
  158. scipy/interpolate/_ndbspline.py +13 -18
  159. scipy/interpolate/_ndgriddata.py +5 -8
  160. scipy/interpolate/_polyint.py +95 -31
  161. scipy/interpolate/_ppoly.cpython-312-aarch64-linux-musl.so +0 -0
  162. scipy/interpolate/_rbf.py +2 -2
  163. scipy/interpolate/_rbfinterp.py +1 -1
  164. scipy/interpolate/_rbfinterp_pythran.cpython-312-aarch64-linux-musl.so +0 -0
  165. scipy/interpolate/_rgi.py +31 -26
  166. scipy/interpolate/_rgi_cython.cpython-312-aarch64-linux-musl.so +0 -0
  167. scipy/interpolate/dfitpack.py +0 -20
  168. scipy/interpolate/interpnd.py +1 -2
  169. scipy/interpolate/tests/test_bary_rational.py +2 -2
  170. scipy/interpolate/tests/test_bsplines.py +97 -1
  171. scipy/interpolate/tests/test_fitpack2.py +39 -1
  172. scipy/interpolate/tests/test_interpnd.py +32 -20
  173. scipy/interpolate/tests/test_interpolate.py +48 -4
  174. scipy/interpolate/tests/test_rgi.py +2 -1
  175. scipy/io/_fast_matrix_market/__init__.py +2 -0
  176. scipy/io/_fast_matrix_market/_fmm_core.cpython-312-aarch64-linux-musl.so +0 -0
  177. scipy/io/_harwell_boeing/_fortran_format_parser.py +19 -16
  178. scipy/io/_harwell_boeing/hb.py +7 -11
  179. scipy/io/_idl.py +5 -7
  180. scipy/io/_netcdf.py +15 -5
  181. scipy/io/_test_fortran.cpython-312-aarch64-linux-musl.so +0 -0
  182. scipy/io/arff/tests/test_arffread.py +3 -3
  183. scipy/io/matlab/__init__.py +5 -3
  184. scipy/io/matlab/_mio.py +4 -1
  185. scipy/io/matlab/_mio5.py +19 -13
  186. scipy/io/matlab/_mio5_utils.cpython-312-aarch64-linux-musl.so +0 -0
  187. scipy/io/matlab/_mio_utils.cpython-312-aarch64-linux-musl.so +0 -0
  188. scipy/io/matlab/_miobase.py +4 -1
  189. scipy/io/matlab/_streams.cpython-312-aarch64-linux-musl.so +0 -0
  190. scipy/io/matlab/tests/test_mio.py +46 -18
  191. scipy/io/matlab/tests/test_mio_funcs.py +1 -1
  192. scipy/io/tests/test_mmio.py +7 -1
  193. scipy/io/tests/test_wavfile.py +41 -0
  194. scipy/io/wavfile.py +57 -10
  195. scipy/linalg/_basic.py +113 -86
  196. scipy/linalg/_cythonized_array_utils.cpython-312-aarch64-linux-musl.so +0 -0
  197. scipy/linalg/_decomp.py +22 -9
  198. scipy/linalg/_decomp_cholesky.py +28 -13
  199. scipy/linalg/_decomp_cossin.py +45 -30
  200. scipy/linalg/_decomp_interpolative.cpython-312-aarch64-linux-musl.so +0 -0
  201. scipy/linalg/_decomp_ldl.py +4 -1
  202. scipy/linalg/_decomp_lu.py +18 -6
  203. scipy/linalg/_decomp_lu_cython.cpython-312-aarch64-linux-musl.so +0 -0
  204. scipy/linalg/_decomp_polar.py +2 -0
  205. scipy/linalg/_decomp_qr.py +6 -2
  206. scipy/linalg/_decomp_qz.py +3 -0
  207. scipy/linalg/_decomp_schur.py +3 -1
  208. scipy/linalg/_decomp_svd.py +13 -2
  209. scipy/linalg/_decomp_update.cpython-312-aarch64-linux-musl.so +0 -0
  210. scipy/linalg/_expm_frechet.py +4 -0
  211. scipy/linalg/_fblas.cpython-312-aarch64-linux-musl.so +0 -0
  212. scipy/linalg/_flapack.cpython-312-aarch64-linux-musl.so +0 -0
  213. scipy/linalg/_linalg_pythran.cpython-312-aarch64-linux-musl.so +0 -0
  214. scipy/linalg/_matfuncs.py +187 -4
  215. scipy/linalg/_matfuncs_expm.cpython-312-aarch64-linux-musl.so +0 -0
  216. scipy/linalg/_matfuncs_schur_sqrtm.cpython-312-aarch64-linux-musl.so +0 -0
  217. scipy/linalg/_matfuncs_sqrtm.py +1 -99
  218. scipy/linalg/_matfuncs_sqrtm_triu.cpython-312-aarch64-linux-musl.so +0 -0
  219. scipy/linalg/_procrustes.py +2 -0
  220. scipy/linalg/_sketches.py +17 -6
  221. scipy/linalg/_solve_toeplitz.cpython-312-aarch64-linux-musl.so +0 -0
  222. scipy/linalg/_solvers.py +7 -2
  223. scipy/linalg/_special_matrices.py +26 -36
  224. scipy/linalg/cython_blas.cpython-312-aarch64-linux-musl.so +0 -0
  225. scipy/linalg/cython_lapack.cpython-312-aarch64-linux-musl.so +0 -0
  226. scipy/linalg/lapack.py +22 -2
  227. scipy/linalg/tests/_cython_examples/meson.build +7 -0
  228. scipy/linalg/tests/test_basic.py +31 -16
  229. scipy/linalg/tests/test_batch.py +588 -0
  230. scipy/linalg/tests/test_cythonized_array_utils.py +0 -2
  231. scipy/linalg/tests/test_decomp.py +40 -3
  232. scipy/linalg/tests/test_decomp_cossin.py +14 -0
  233. scipy/linalg/tests/test_decomp_ldl.py +1 -1
  234. scipy/linalg/tests/test_lapack.py +115 -7
  235. scipy/linalg/tests/test_matfuncs.py +157 -102
  236. scipy/linalg/tests/test_procrustes.py +0 -7
  237. scipy/linalg/tests/test_solve_toeplitz.py +1 -1
  238. scipy/linalg/tests/test_special_matrices.py +1 -5
  239. scipy/ndimage/__init__.py +1 -0
  240. scipy/ndimage/_ctest.cpython-312-aarch64-linux-musl.so +0 -0
  241. scipy/ndimage/_cytest.cpython-312-aarch64-linux-musl.so +0 -0
  242. scipy/ndimage/_delegators.py +8 -2
  243. scipy/ndimage/_filters.py +453 -5
  244. scipy/ndimage/_interpolation.py +36 -6
  245. scipy/ndimage/_measurements.py +4 -2
  246. scipy/ndimage/_morphology.py +5 -0
  247. scipy/ndimage/_nd_image.cpython-312-aarch64-linux-musl.so +0 -0
  248. scipy/ndimage/_ni_docstrings.py +5 -1
  249. scipy/ndimage/_ni_label.cpython-312-aarch64-linux-musl.so +0 -0
  250. scipy/ndimage/_ni_support.py +1 -5
  251. scipy/ndimage/_rank_filter_1d.cpython-312-aarch64-linux-musl.so +0 -0
  252. scipy/ndimage/_support_alternative_backends.py +18 -6
  253. scipy/ndimage/tests/test_filters.py +370 -259
  254. scipy/ndimage/tests/test_fourier.py +7 -9
  255. scipy/ndimage/tests/test_interpolation.py +68 -61
  256. scipy/ndimage/tests/test_measurements.py +18 -35
  257. scipy/ndimage/tests/test_morphology.py +143 -131
  258. scipy/ndimage/tests/test_splines.py +1 -3
  259. scipy/odr/__odrpack.cpython-312-aarch64-linux-musl.so +0 -0
  260. scipy/optimize/_basinhopping.py +13 -7
  261. scipy/optimize/_bglu_dense.cpython-312-aarch64-linux-musl.so +0 -0
  262. scipy/optimize/_bracket.py +17 -24
  263. scipy/optimize/_chandrupatla.py +9 -10
  264. scipy/optimize/_cobyla_py.py +104 -123
  265. scipy/optimize/_constraints.py +14 -10
  266. scipy/optimize/_differentiable_functions.py +371 -230
  267. scipy/optimize/_differentialevolution.py +4 -3
  268. scipy/optimize/_direct.cpython-312-aarch64-linux-musl.so +0 -0
  269. scipy/optimize/_dual_annealing.py +1 -1
  270. scipy/optimize/_elementwise.py +1 -4
  271. scipy/optimize/_group_columns.cpython-312-aarch64-linux-musl.so +0 -0
  272. scipy/optimize/_highspy/_core.cpython-312-aarch64-linux-musl.so +0 -0
  273. scipy/optimize/_highspy/_highs_options.cpython-312-aarch64-linux-musl.so +0 -0
  274. scipy/optimize/_lbfgsb.cpython-312-aarch64-linux-musl.so +0 -0
  275. scipy/optimize/_lbfgsb_py.py +57 -16
  276. scipy/optimize/_linprog_doc.py +2 -2
  277. scipy/optimize/_linprog_highs.py +2 -2
  278. scipy/optimize/_linprog_ip.py +25 -10
  279. scipy/optimize/_linprog_util.py +14 -16
  280. scipy/optimize/_lsap.cpython-312-aarch64-linux-musl.so +0 -0
  281. scipy/optimize/_lsq/common.py +3 -3
  282. scipy/optimize/_lsq/dogbox.py +16 -2
  283. scipy/optimize/_lsq/givens_elimination.cpython-312-aarch64-linux-musl.so +0 -0
  284. scipy/optimize/_lsq/least_squares.py +198 -126
  285. scipy/optimize/_lsq/lsq_linear.py +6 -6
  286. scipy/optimize/_lsq/trf.py +35 -8
  287. scipy/optimize/_milp.py +3 -1
  288. scipy/optimize/_minimize.py +105 -36
  289. scipy/optimize/_minpack.cpython-312-aarch64-linux-musl.so +0 -0
  290. scipy/optimize/_minpack_py.py +21 -14
  291. scipy/optimize/_moduleTNC.cpython-312-aarch64-linux-musl.so +0 -0
  292. scipy/optimize/_nnls.py +20 -21
  293. scipy/optimize/_nonlin.py +34 -3
  294. scipy/optimize/_numdiff.py +288 -110
  295. scipy/optimize/_optimize.py +86 -48
  296. scipy/optimize/_pava_pybind.cpython-312-aarch64-linux-musl.so +0 -0
  297. scipy/optimize/_remove_redundancy.py +5 -5
  298. scipy/optimize/_root_scalar.py +1 -1
  299. scipy/optimize/_shgo.py +6 -0
  300. scipy/optimize/_shgo_lib/_complex.py +1 -1
  301. scipy/optimize/_slsqp_py.py +216 -124
  302. scipy/optimize/_slsqplib.cpython-312-aarch64-linux-musl.so +0 -0
  303. scipy/optimize/_spectral.py +1 -1
  304. scipy/optimize/_tnc.py +8 -1
  305. scipy/optimize/_trlib/_trlib.cpython-312-aarch64-linux-musl.so +0 -0
  306. scipy/optimize/_trustregion.py +20 -6
  307. scipy/optimize/_trustregion_constr/canonical_constraint.py +7 -7
  308. scipy/optimize/_trustregion_constr/equality_constrained_sqp.py +1 -1
  309. scipy/optimize/_trustregion_constr/minimize_trustregion_constr.py +11 -3
  310. scipy/optimize/_trustregion_constr/projections.py +12 -8
  311. scipy/optimize/_trustregion_constr/qp_subproblem.py +9 -9
  312. scipy/optimize/_trustregion_constr/tests/test_projections.py +7 -7
  313. scipy/optimize/_trustregion_constr/tests/test_qp_subproblem.py +77 -77
  314. scipy/optimize/_trustregion_constr/tr_interior_point.py +5 -5
  315. scipy/optimize/_trustregion_exact.py +0 -1
  316. scipy/optimize/_zeros.cpython-312-aarch64-linux-musl.so +0 -0
  317. scipy/optimize/_zeros_py.py +97 -17
  318. scipy/optimize/cython_optimize/_zeros.cpython-312-aarch64-linux-musl.so +0 -0
  319. scipy/optimize/slsqp.py +0 -1
  320. scipy/optimize/tests/test__basinhopping.py +1 -1
  321. scipy/optimize/tests/test__differential_evolution.py +4 -4
  322. scipy/optimize/tests/test__linprog_clean_inputs.py +5 -3
  323. scipy/optimize/tests/test__numdiff.py +66 -22
  324. scipy/optimize/tests/test__remove_redundancy.py +2 -2
  325. scipy/optimize/tests/test__shgo.py +9 -1
  326. scipy/optimize/tests/test_bracket.py +36 -46
  327. scipy/optimize/tests/test_chandrupatla.py +133 -135
  328. scipy/optimize/tests/test_cobyla.py +74 -45
  329. scipy/optimize/tests/test_constraints.py +1 -1
  330. scipy/optimize/tests/test_differentiable_functions.py +226 -6
  331. scipy/optimize/tests/test_lbfgsb_hessinv.py +22 -0
  332. scipy/optimize/tests/test_least_squares.py +125 -13
  333. scipy/optimize/tests/test_linear_assignment.py +3 -3
  334. scipy/optimize/tests/test_linprog.py +3 -3
  335. scipy/optimize/tests/test_lsq_linear.py +6 -6
  336. scipy/optimize/tests/test_minimize_constrained.py +2 -2
  337. scipy/optimize/tests/test_minpack.py +4 -4
  338. scipy/optimize/tests/test_nnls.py +43 -3
  339. scipy/optimize/tests/test_nonlin.py +36 -0
  340. scipy/optimize/tests/test_optimize.py +95 -17
  341. scipy/optimize/tests/test_slsqp.py +36 -4
  342. scipy/optimize/tests/test_zeros.py +34 -1
  343. scipy/signal/__init__.py +12 -23
  344. scipy/signal/_delegators.py +568 -0
  345. scipy/signal/_filter_design.py +459 -241
  346. scipy/signal/_fir_filter_design.py +262 -90
  347. scipy/signal/_lti_conversion.py +3 -2
  348. scipy/signal/_ltisys.py +118 -91
  349. scipy/signal/_max_len_seq_inner.cpython-312-aarch64-linux-musl.so +0 -0
  350. scipy/signal/_peak_finding_utils.cpython-312-aarch64-linux-musl.so +0 -0
  351. scipy/signal/_polyutils.py +172 -0
  352. scipy/signal/_short_time_fft.py +519 -70
  353. scipy/signal/_signal_api.py +30 -0
  354. scipy/signal/_signaltools.py +719 -399
  355. scipy/signal/_sigtools.cpython-312-aarch64-linux-musl.so +0 -0
  356. scipy/signal/_sosfilt.cpython-312-aarch64-linux-musl.so +0 -0
  357. scipy/signal/_spectral_py.py +230 -50
  358. scipy/signal/_spline.cpython-312-aarch64-linux-musl.so +0 -0
  359. scipy/signal/_spline_filters.py +108 -68
  360. scipy/signal/_support_alternative_backends.py +73 -0
  361. scipy/signal/_upfirdn.py +4 -1
  362. scipy/signal/_upfirdn_apply.cpython-312-aarch64-linux-musl.so +0 -0
  363. scipy/signal/_waveforms.py +2 -11
  364. scipy/signal/_wavelets.py +1 -1
  365. scipy/signal/fir_filter_design.py +1 -0
  366. scipy/signal/spline.py +4 -11
  367. scipy/signal/tests/_scipy_spectral_test_shim.py +2 -171
  368. scipy/signal/tests/test_bsplines.py +114 -79
  369. scipy/signal/tests/test_cont2discrete.py +9 -2
  370. scipy/signal/tests/test_filter_design.py +721 -481
  371. scipy/signal/tests/test_fir_filter_design.py +332 -140
  372. scipy/signal/tests/test_savitzky_golay.py +4 -3
  373. scipy/signal/tests/test_short_time_fft.py +221 -3
  374. scipy/signal/tests/test_signaltools.py +2144 -1348
  375. scipy/signal/tests/test_spectral.py +50 -6
  376. scipy/signal/tests/test_splines.py +161 -96
  377. scipy/signal/tests/test_upfirdn.py +84 -50
  378. scipy/signal/tests/test_waveforms.py +20 -0
  379. scipy/signal/tests/test_windows.py +607 -466
  380. scipy/signal/windows/_windows.py +287 -148
  381. scipy/sparse/__init__.py +23 -4
  382. scipy/sparse/_base.py +270 -108
  383. scipy/sparse/_bsr.py +7 -4
  384. scipy/sparse/_compressed.py +59 -231
  385. scipy/sparse/_construct.py +90 -38
  386. scipy/sparse/_coo.py +115 -181
  387. scipy/sparse/_csc.py +4 -4
  388. scipy/sparse/_csparsetools.cpython-312-aarch64-linux-musl.so +0 -0
  389. scipy/sparse/_csr.py +2 -2
  390. scipy/sparse/_data.py +48 -48
  391. scipy/sparse/_dia.py +105 -18
  392. scipy/sparse/_dok.py +0 -23
  393. scipy/sparse/_index.py +4 -4
  394. scipy/sparse/_matrix.py +23 -0
  395. scipy/sparse/_sparsetools.cpython-312-aarch64-linux-musl.so +0 -0
  396. scipy/sparse/_sputils.py +37 -22
  397. scipy/sparse/base.py +0 -9
  398. scipy/sparse/bsr.py +0 -14
  399. scipy/sparse/compressed.py +0 -23
  400. scipy/sparse/construct.py +0 -6
  401. scipy/sparse/coo.py +0 -14
  402. scipy/sparse/csc.py +0 -3
  403. scipy/sparse/csgraph/_flow.cpython-312-aarch64-linux-musl.so +0 -0
  404. scipy/sparse/csgraph/_matching.cpython-312-aarch64-linux-musl.so +0 -0
  405. scipy/sparse/csgraph/_min_spanning_tree.cpython-312-aarch64-linux-musl.so +0 -0
  406. scipy/sparse/csgraph/_reordering.cpython-312-aarch64-linux-musl.so +0 -0
  407. scipy/sparse/csgraph/_shortest_path.cpython-312-aarch64-linux-musl.so +0 -0
  408. scipy/sparse/csgraph/_tools.cpython-312-aarch64-linux-musl.so +0 -0
  409. scipy/sparse/csgraph/_traversal.cpython-312-aarch64-linux-musl.so +0 -0
  410. scipy/sparse/csgraph/tests/test_matching.py +14 -2
  411. scipy/sparse/csgraph/tests/test_pydata_sparse.py +4 -1
  412. scipy/sparse/csgraph/tests/test_shortest_path.py +83 -27
  413. scipy/sparse/csr.py +0 -5
  414. scipy/sparse/data.py +1 -6
  415. scipy/sparse/dia.py +0 -7
  416. scipy/sparse/dok.py +0 -10
  417. scipy/sparse/linalg/_dsolve/_superlu.cpython-312-aarch64-linux-musl.so +0 -0
  418. scipy/sparse/linalg/_dsolve/linsolve.py +9 -0
  419. scipy/sparse/linalg/_dsolve/tests/test_linsolve.py +35 -28
  420. scipy/sparse/linalg/_eigen/arpack/_arpack.cpython-312-aarch64-linux-musl.so +0 -0
  421. scipy/sparse/linalg/_eigen/arpack/arpack.py +23 -17
  422. scipy/sparse/linalg/_eigen/lobpcg/lobpcg.py +6 -6
  423. scipy/sparse/linalg/_interface.py +17 -18
  424. scipy/sparse/linalg/_isolve/_gcrotmk.py +4 -4
  425. scipy/sparse/linalg/_isolve/iterative.py +51 -45
  426. scipy/sparse/linalg/_isolve/lgmres.py +6 -6
  427. scipy/sparse/linalg/_isolve/minres.py +5 -5
  428. scipy/sparse/linalg/_isolve/tfqmr.py +7 -7
  429. scipy/sparse/linalg/_isolve/utils.py +2 -8
  430. scipy/sparse/linalg/_matfuncs.py +1 -1
  431. scipy/sparse/linalg/_norm.py +1 -1
  432. scipy/sparse/linalg/_propack/_cpropack.cpython-312-aarch64-linux-musl.so +0 -0
  433. scipy/sparse/linalg/_propack/_dpropack.cpython-312-aarch64-linux-musl.so +0 -0
  434. scipy/sparse/linalg/_propack/_spropack.cpython-312-aarch64-linux-musl.so +0 -0
  435. scipy/sparse/linalg/_propack/_zpropack.cpython-312-aarch64-linux-musl.so +0 -0
  436. scipy/sparse/linalg/_special_sparse_arrays.py +39 -38
  437. scipy/sparse/linalg/tests/test_pydata_sparse.py +14 -0
  438. scipy/sparse/tests/test_arithmetic1d.py +5 -2
  439. scipy/sparse/tests/test_base.py +214 -42
  440. scipy/sparse/tests/test_common1d.py +7 -7
  441. scipy/sparse/tests/test_construct.py +1 -1
  442. scipy/sparse/tests/test_coo.py +272 -4
  443. scipy/sparse/tests/test_sparsetools.py +5 -0
  444. scipy/sparse/tests/test_sputils.py +36 -7
  445. scipy/spatial/_ckdtree.cpython-312-aarch64-linux-musl.so +0 -0
  446. scipy/spatial/_distance_pybind.cpython-312-aarch64-linux-musl.so +0 -0
  447. scipy/spatial/_distance_wrap.cpython-312-aarch64-linux-musl.so +0 -0
  448. scipy/spatial/_hausdorff.cpython-312-aarch64-linux-musl.so +0 -0
  449. scipy/spatial/_qhull.cpython-312-aarch64-linux-musl.so +0 -0
  450. scipy/spatial/_voronoi.cpython-312-aarch64-linux-musl.so +0 -0
  451. scipy/spatial/distance.py +49 -42
  452. scipy/spatial/tests/test_distance.py +15 -1
  453. scipy/spatial/tests/test_kdtree.py +1 -0
  454. scipy/spatial/tests/test_qhull.py +7 -2
  455. scipy/spatial/transform/__init__.py +5 -3
  456. scipy/spatial/transform/_rigid_transform.cpython-312-aarch64-linux-musl.so +0 -0
  457. scipy/spatial/transform/_rotation.cpython-312-aarch64-linux-musl.so +0 -0
  458. scipy/spatial/transform/tests/test_rigid_transform.py +1221 -0
  459. scipy/spatial/transform/tests/test_rotation.py +1213 -832
  460. scipy/spatial/transform/tests/test_rotation_groups.py +3 -3
  461. scipy/spatial/transform/tests/test_rotation_spline.py +29 -8
  462. scipy/special/__init__.py +1 -47
  463. scipy/special/_add_newdocs.py +34 -772
  464. scipy/special/_basic.py +22 -25
  465. scipy/special/_comb.cpython-312-aarch64-linux-musl.so +0 -0
  466. scipy/special/_ellip_harm_2.cpython-312-aarch64-linux-musl.so +0 -0
  467. scipy/special/_gufuncs.cpython-312-aarch64-linux-musl.so +0 -0
  468. scipy/special/_logsumexp.py +67 -58
  469. scipy/special/_orthogonal.pyi +1 -1
  470. scipy/special/_specfun.cpython-312-aarch64-linux-musl.so +0 -0
  471. scipy/special/_special_ufuncs.cpython-312-aarch64-linux-musl.so +0 -0
  472. scipy/special/_spherical_bessel.py +4 -4
  473. scipy/special/_support_alternative_backends.py +212 -119
  474. scipy/special/_test_internal.cpython-312-aarch64-linux-musl.so +0 -0
  475. scipy/special/_testutils.py +4 -4
  476. scipy/special/_ufuncs.cpython-312-aarch64-linux-musl.so +0 -0
  477. scipy/special/_ufuncs.pyi +1 -0
  478. scipy/special/_ufuncs.pyx +215 -1400
  479. scipy/special/_ufuncs_cxx.cpython-312-aarch64-linux-musl.so +0 -0
  480. scipy/special/_ufuncs_cxx.pxd +2 -15
  481. scipy/special/_ufuncs_cxx.pyx +5 -44
  482. scipy/special/_ufuncs_cxx_defs.h +2 -16
  483. scipy/special/_ufuncs_defs.h +0 -8
  484. scipy/special/cython_special.cpython-312-aarch64-linux-musl.so +0 -0
  485. scipy/special/cython_special.pxd +1 -1
  486. scipy/special/tests/_cython_examples/meson.build +10 -1
  487. scipy/special/tests/test_basic.py +153 -20
  488. scipy/special/tests/test_boost_ufuncs.py +3 -0
  489. scipy/special/tests/test_cdflib.py +35 -11
  490. scipy/special/tests/test_gammainc.py +16 -0
  491. scipy/special/tests/test_hyp2f1.py +2 -2
  492. scipy/special/tests/test_log1mexp.py +85 -0
  493. scipy/special/tests/test_logsumexp.py +206 -64
  494. scipy/special/tests/test_mpmath.py +1 -0
  495. scipy/special/tests/test_nan_inputs.py +1 -1
  496. scipy/special/tests/test_orthogonal.py +17 -18
  497. scipy/special/tests/test_sf_error.py +3 -2
  498. scipy/special/tests/test_sph_harm.py +6 -7
  499. scipy/special/tests/test_support_alternative_backends.py +211 -76
  500. scipy/stats/__init__.py +4 -1
  501. scipy/stats/_ansari_swilk_statistics.cpython-312-aarch64-linux-musl.so +0 -0
  502. scipy/stats/_axis_nan_policy.py +5 -12
  503. scipy/stats/_biasedurn.cpython-312-aarch64-linux-musl.so +0 -0
  504. scipy/stats/_continued_fraction.py +387 -0
  505. scipy/stats/_continuous_distns.py +277 -310
  506. scipy/stats/_correlation.py +1 -1
  507. scipy/stats/_covariance.py +6 -3
  508. scipy/stats/_discrete_distns.py +39 -32
  509. scipy/stats/_distn_infrastructure.py +39 -12
  510. scipy/stats/_distribution_infrastructure.py +900 -238
  511. scipy/stats/_entropy.py +9 -10
  512. scipy/{_lib → stats}/_finite_differences.py +1 -1
  513. scipy/stats/_hypotests.py +83 -50
  514. scipy/stats/_kde.py +53 -49
  515. scipy/stats/_ksstats.py +1 -1
  516. scipy/stats/_levy_stable/__init__.py +7 -15
  517. scipy/stats/_levy_stable/levyst.cpython-312-aarch64-linux-musl.so +0 -0
  518. scipy/stats/_morestats.py +118 -73
  519. scipy/stats/_mstats_basic.py +13 -17
  520. scipy/stats/_mstats_extras.py +8 -8
  521. scipy/stats/_multivariate.py +89 -113
  522. scipy/stats/_new_distributions.py +97 -20
  523. scipy/stats/_page_trend_test.py +12 -5
  524. scipy/stats/_probability_distribution.py +265 -43
  525. scipy/stats/_qmc.py +14 -9
  526. scipy/stats/_qmc_cy.cpython-312-aarch64-linux-musl.so +0 -0
  527. scipy/stats/_qmvnt.py +16 -95
  528. scipy/stats/_qmvnt_cy.cpython-312-aarch64-linux-musl.so +0 -0
  529. scipy/stats/_quantile.py +335 -0
  530. scipy/stats/_rcont/rcont.cpython-312-aarch64-linux-musl.so +0 -0
  531. scipy/stats/_resampling.py +4 -29
  532. scipy/stats/_sampling.py +1 -1
  533. scipy/stats/_sobol.cpython-312-aarch64-linux-musl.so +0 -0
  534. scipy/stats/_stats.cpython-312-aarch64-linux-musl.so +0 -0
  535. scipy/stats/_stats_mstats_common.py +21 -2
  536. scipy/stats/_stats_py.py +550 -476
  537. scipy/stats/_stats_pythran.cpython-312-aarch64-linux-musl.so +0 -0
  538. scipy/stats/_unuran/unuran_wrapper.cpython-312-aarch64-linux-musl.so +0 -0
  539. scipy/stats/_unuran/unuran_wrapper.pyi +2 -1
  540. scipy/stats/_variation.py +6 -8
  541. scipy/stats/_wilcoxon.py +13 -7
  542. scipy/stats/tests/common_tests.py +6 -4
  543. scipy/stats/tests/test_axis_nan_policy.py +62 -24
  544. scipy/stats/tests/test_continued_fraction.py +173 -0
  545. scipy/stats/tests/test_continuous.py +379 -60
  546. scipy/stats/tests/test_continuous_basic.py +18 -12
  547. scipy/stats/tests/test_discrete_basic.py +14 -8
  548. scipy/stats/tests/test_discrete_distns.py +16 -16
  549. scipy/stats/tests/test_distributions.py +95 -75
  550. scipy/stats/tests/test_entropy.py +40 -48
  551. scipy/stats/tests/test_fit.py +4 -3
  552. scipy/stats/tests/test_hypotests.py +153 -24
  553. scipy/stats/tests/test_kdeoth.py +109 -41
  554. scipy/stats/tests/test_marray.py +289 -0
  555. scipy/stats/tests/test_morestats.py +79 -47
  556. scipy/stats/tests/test_mstats_basic.py +3 -3
  557. scipy/stats/tests/test_multivariate.py +434 -83
  558. scipy/stats/tests/test_qmc.py +13 -10
  559. scipy/stats/tests/test_quantile.py +199 -0
  560. scipy/stats/tests/test_rank.py +119 -112
  561. scipy/stats/tests/test_resampling.py +47 -56
  562. scipy/stats/tests/test_sampling.py +9 -4
  563. scipy/stats/tests/test_stats.py +799 -939
  564. scipy/stats/tests/test_variation.py +8 -6
  565. scipy/version.py +2 -2
  566. {scipy-1.15.3.dist-info → scipy-1.16.0rc2.dist-info}/LICENSE.txt +4 -4
  567. {scipy-1.15.3.dist-info → scipy-1.16.0rc2.dist-info}/METADATA +11 -11
  568. {scipy-1.15.3.dist-info → scipy-1.16.0rc2.dist-info}/RECORD +1262 -1269
  569. scipy.libs/libgcc_s-69c45f16.so.1 +0 -0
  570. scipy.libs/libgfortran-db0b6589.so.5.0.0 +0 -0
  571. scipy.libs/{libstdc++-1b614e01.so.6.0.32 → libstdc++-1f1a71be.so.6.0.33} +0 -0
  572. scipy/_lib/array_api_extra/_funcs.py +0 -484
  573. scipy/_lib/array_api_extra/_typing.py +0 -8
  574. scipy/interpolate/_bspl.cpython-312-aarch64-linux-musl.so +0 -0
  575. scipy/optimize/_cobyla.cpython-312-aarch64-linux-musl.so +0 -0
  576. scipy/optimize/_cython_nnls.cpython-312-aarch64-linux-musl.so +0 -0
  577. scipy/optimize/_slsqp.cpython-312-aarch64-linux-musl.so +0 -0
  578. scipy/spatial/qhull_src/COPYING.txt +0 -38
  579. scipy/special/libsf_error_state.so +0 -0
  580. scipy/special/tests/test_log_softmax.py +0 -109
  581. scipy/special/tests/test_xsf_cuda.py +0 -114
  582. scipy/special/xsf/binom.h +0 -89
  583. scipy/special/xsf/cdflib.h +0 -100
  584. scipy/special/xsf/cephes/airy.h +0 -307
  585. scipy/special/xsf/cephes/besselpoly.h +0 -51
  586. scipy/special/xsf/cephes/beta.h +0 -257
  587. scipy/special/xsf/cephes/cbrt.h +0 -131
  588. scipy/special/xsf/cephes/chbevl.h +0 -85
  589. scipy/special/xsf/cephes/chdtr.h +0 -193
  590. scipy/special/xsf/cephes/const.h +0 -87
  591. scipy/special/xsf/cephes/ellie.h +0 -293
  592. scipy/special/xsf/cephes/ellik.h +0 -251
  593. scipy/special/xsf/cephes/ellpe.h +0 -107
  594. scipy/special/xsf/cephes/ellpk.h +0 -117
  595. scipy/special/xsf/cephes/expn.h +0 -260
  596. scipy/special/xsf/cephes/gamma.h +0 -398
  597. scipy/special/xsf/cephes/hyp2f1.h +0 -596
  598. scipy/special/xsf/cephes/hyperg.h +0 -361
  599. scipy/special/xsf/cephes/i0.h +0 -149
  600. scipy/special/xsf/cephes/i1.h +0 -158
  601. scipy/special/xsf/cephes/igam.h +0 -421
  602. scipy/special/xsf/cephes/igam_asymp_coeff.h +0 -195
  603. scipy/special/xsf/cephes/igami.h +0 -313
  604. scipy/special/xsf/cephes/j0.h +0 -225
  605. scipy/special/xsf/cephes/j1.h +0 -198
  606. scipy/special/xsf/cephes/jv.h +0 -715
  607. scipy/special/xsf/cephes/k0.h +0 -164
  608. scipy/special/xsf/cephes/k1.h +0 -163
  609. scipy/special/xsf/cephes/kn.h +0 -243
  610. scipy/special/xsf/cephes/lanczos.h +0 -112
  611. scipy/special/xsf/cephes/ndtr.h +0 -275
  612. scipy/special/xsf/cephes/poch.h +0 -85
  613. scipy/special/xsf/cephes/polevl.h +0 -167
  614. scipy/special/xsf/cephes/psi.h +0 -194
  615. scipy/special/xsf/cephes/rgamma.h +0 -111
  616. scipy/special/xsf/cephes/scipy_iv.h +0 -811
  617. scipy/special/xsf/cephes/shichi.h +0 -248
  618. scipy/special/xsf/cephes/sici.h +0 -224
  619. scipy/special/xsf/cephes/sindg.h +0 -221
  620. scipy/special/xsf/cephes/tandg.h +0 -139
  621. scipy/special/xsf/cephes/trig.h +0 -58
  622. scipy/special/xsf/cephes/unity.h +0 -186
  623. scipy/special/xsf/cephes/zeta.h +0 -172
  624. scipy/special/xsf/config.h +0 -304
  625. scipy/special/xsf/digamma.h +0 -205
  626. scipy/special/xsf/error.h +0 -57
  627. scipy/special/xsf/evalpoly.h +0 -47
  628. scipy/special/xsf/expint.h +0 -266
  629. scipy/special/xsf/hyp2f1.h +0 -694
  630. scipy/special/xsf/iv_ratio.h +0 -173
  631. scipy/special/xsf/lambertw.h +0 -150
  632. scipy/special/xsf/loggamma.h +0 -163
  633. scipy/special/xsf/sici.h +0 -200
  634. scipy/special/xsf/tools.h +0 -427
  635. scipy/special/xsf/trig.h +0 -164
  636. scipy/special/xsf/wright_bessel.h +0 -843
  637. scipy/special/xsf/zlog1.h +0 -35
  638. scipy/stats/_mvn.cpython-312-aarch64-linux-musl.so +0 -0
  639. scipy.libs/libgcc_s-7393e603.so.1 +0 -0
  640. scipy.libs/libgfortran-eb933d8e.so.5.0.0 +0 -0
  641. {scipy-1.15.3.dist-info → scipy-1.16.0rc2.dist-info}/WHEEL +0 -0
scipy/signal/_ltisys.py CHANGED
@@ -1354,8 +1354,8 @@ class StateSpace(LinearTimeInvariant):
1354
1354
  )
1355
1355
 
1356
1356
  def _check_binop_other(self, other):
1357
- return isinstance(other, (StateSpace, np.ndarray, float, complex,
1358
- np.number, int))
1357
+ return isinstance(other, StateSpace | np.ndarray | float | complex |
1358
+ np.number | int)
1359
1359
 
1360
1360
  def __mul__(self, other):
1361
1361
  """
@@ -1895,7 +1895,7 @@ def lsim(system, U, T, X0=None, interp=True):
1895
1895
  raise ValueError("Initial time must be nonnegative")
1896
1896
 
1897
1897
  no_input = (U is None or
1898
- (isinstance(U, (int, float)) and U == 0.) or
1898
+ (isinstance(U, int | float) and U == 0.) or
1899
1899
  not np.any(U))
1900
1900
 
1901
1901
  if n_steps == 1:
@@ -2260,7 +2260,7 @@ def freqresp(system, w=None, n=10000):
2260
2260
  >>> plt.show()
2261
2261
  """
2262
2262
  if isinstance(system, lti):
2263
- if isinstance(system, (TransferFunction, ZerosPolesGain)):
2263
+ if isinstance(system, TransferFunction | ZerosPolesGain):
2264
2264
  sys = system
2265
2265
  else:
2266
2266
  sys = system._as_zpk()
@@ -2317,11 +2317,13 @@ def _valid_inputs(A, B, poles, method, rtol, maxiter):
2317
2317
  if A.shape[0] != A.shape[1]:
2318
2318
  raise ValueError("A must be square")
2319
2319
  if len(poles) > A.shape[0]:
2320
- raise ValueError("maximum number of poles is %d but you asked for %d" %
2321
- (A.shape[0], len(poles)))
2320
+ raise ValueError(
2321
+ f"maximum number of poles is {A.shape[0]} but you asked for {len(poles)}"
2322
+ )
2322
2323
  if len(poles) < A.shape[0]:
2323
- raise ValueError("number of poles is %d but you should provide %d" %
2324
- (len(poles), A.shape[0]))
2324
+ raise ValueError(
2325
+ f"number of poles is {len(poles)} but you should provide {A.shape[0]}"
2326
+ )
2325
2327
  r = np.linalg.matrix_rank(B)
2326
2328
  for p in poles:
2327
2329
  if sum(p == poles) > r:
@@ -3032,20 +3034,24 @@ def place_poles(A, B, poles, method="YT", rtol=1e-3, maxiter=30):
3032
3034
 
3033
3035
 
3034
3036
  def dlsim(system, u, t=None, x0=None):
3035
- """
3036
- Simulate output of a discrete-time linear system.
3037
+ r"""Simulate output of a discrete-time linear system.
3037
3038
 
3038
3039
  Parameters
3039
3040
  ----------
3040
- system : tuple of array_like or instance of `dlti`
3041
- A tuple describing the system.
3042
- The following gives the number of elements in the tuple and
3043
- the interpretation:
3041
+ system : dlti | tuple
3042
+ An instance of the LTI class `dlti` or a tuple describing the system.
3043
+ The number of elements in the tuple determine the interpretation. I.e.:
3044
+
3045
+ * ``system``: Instance of LTI class `dlti`. Note that derived instances, such
3046
+ as instances of `TransferFunction`, `ZerosPolesGain`, or `StateSpace`, are
3047
+ allowed as well.
3048
+ * ``(num, den, dt)``: Rational polynomial as described in `TransferFunction`.
3049
+ The coefficients of the polynomials should be specified in descending
3050
+ exponent order, e.g., z² + 3z + 5 would be represented as ``[1, 3, 5]``.
3051
+ * ``(zeros, poles, gain, dt)``: Zeros, poles, gain form as described
3052
+ in `ZerosPolesGain`.
3053
+ * ``(A, B, C, D, dt)``: State-space form as described in `StateSpace`.
3044
3054
 
3045
- * 1: (instance of `dlti`)
3046
- * 3: (num, den, dt)
3047
- * 4: (zeros, poles, gain, dt)
3048
- * 5: (A, B, C, D, dt)
3049
3055
 
3050
3056
  u : array_like
3051
3057
  An input array describing the input at each time `t` (interpolation is
@@ -3148,20 +3154,23 @@ def dlsim(system, u, t=None, x0=None):
3148
3154
 
3149
3155
 
3150
3156
  def dimpulse(system, x0=None, t=None, n=None):
3151
- """
3152
- Impulse response of discrete-time system.
3157
+ r"""Impulse response of discrete-time system.
3153
3158
 
3154
3159
  Parameters
3155
3160
  ----------
3156
- system : tuple of array_like or instance of `dlti`
3157
- A tuple describing the system.
3158
- The following gives the number of elements in the tuple and
3159
- the interpretation:
3160
-
3161
- * 1: (instance of `dlti`)
3162
- * 3: (num, den, dt)
3163
- * 4: (zeros, poles, gain, dt)
3164
- * 5: (A, B, C, D, dt)
3161
+ system : dlti | tuple
3162
+ An instance of the LTI class `dlti` or a tuple describing the system.
3163
+ The number of elements in the tuple determine the interpretation. I.e.:
3164
+
3165
+ * ``system``: Instance of LTI class `dlti`. Note that derived instances, such
3166
+ as instances of `TransferFunction`, `ZerosPolesGain`, or `StateSpace`, are
3167
+ allowed as well.
3168
+ * ``(num, den, dt)``: Rational polynomial as described in `TransferFunction`.
3169
+ The coefficients of the polynomials should be specified in descending
3170
+ exponent order, e.g., z² + 3z + 5 would be represented as ``[1, 3, 5]``.
3171
+ * ``(zeros, poles, gain, dt)``: Zeros, poles, gain form as described
3172
+ in `ZerosPolesGain`.
3173
+ * ``(A, B, C, D, dt)``: State-space form as described in `StateSpace`.
3165
3174
 
3166
3175
  x0 : array_like, optional
3167
3176
  Initial state-vector. Defaults to zero.
@@ -3187,14 +3196,17 @@ def dimpulse(system, x0=None, t=None, n=None):
3187
3196
  >>> import numpy as np
3188
3197
  >>> from scipy import signal
3189
3198
  >>> import matplotlib.pyplot as plt
3190
-
3191
- >>> butter = signal.dlti(*signal.butter(3, 0.5))
3192
- >>> t, y = signal.dimpulse(butter, n=25)
3193
- >>> plt.step(t, np.squeeze(y))
3194
- >>> plt.grid()
3195
- >>> plt.xlabel('n [samples]')
3196
- >>> plt.ylabel('Amplitude')
3197
-
3199
+ ...
3200
+ >>> dt = 1 # sampling interval is one => time unit is sample number
3201
+ >>> bb, aa = signal.butter(3, 0.25, fs=1/dt)
3202
+ >>> t, y = signal.dimpulse((bb, aa, dt), n=25)
3203
+ ...
3204
+ >>> fig0, ax0 = plt.subplots()
3205
+ >>> ax0.step(t, np.squeeze(y), '.-', where='post')
3206
+ >>> ax0.set_title(r"Impulse Response of a $3^\text{rd}$ Order Butterworth Filter")
3207
+ >>> ax0.set(xlabel='Sample number', ylabel='Amplitude')
3208
+ >>> ax0.grid()
3209
+ >>> plt.show()
3198
3210
  """
3199
3211
  # Convert system to dlti-StateSpace
3200
3212
  if isinstance(system, dlti):
@@ -3235,20 +3247,23 @@ def dimpulse(system, x0=None, t=None, n=None):
3235
3247
 
3236
3248
 
3237
3249
  def dstep(system, x0=None, t=None, n=None):
3238
- """
3239
- Step response of discrete-time system.
3250
+ r"""Step response of discrete-time system.
3240
3251
 
3241
3252
  Parameters
3242
3253
  ----------
3243
- system : tuple of array_like
3244
- A tuple describing the system.
3245
- The following gives the number of elements in the tuple and
3246
- the interpretation:
3247
-
3248
- * 1: (instance of `dlti`)
3249
- * 3: (num, den, dt)
3250
- * 4: (zeros, poles, gain, dt)
3251
- * 5: (A, B, C, D, dt)
3254
+ system : dlti | tuple
3255
+ An instance of the LTI class `dlti` or a tuple describing the system.
3256
+ The number of elements in the tuple determine the interpretation. I.e.:
3257
+
3258
+ * ``system``: Instance of LTI class `dlti`. Note that derived instances, such
3259
+ as instances of `TransferFunction`, `ZerosPolesGain`, or `StateSpace`, are
3260
+ allowed as well.
3261
+ * ``(num, den, dt)``: Rational polynomial as described in `TransferFunction`.
3262
+ The coefficients of the polynomials should be specified in descending
3263
+ exponent order, e.g., z² + 3z + 5 would be represented as ``[1, 3, 5]``.
3264
+ * ``(zeros, poles, gain, dt)``: Zeros, poles, gain form as described
3265
+ in `ZerosPolesGain`.
3266
+ * ``(A, B, C, D, dt)``: State-space form as described in `StateSpace`.
3252
3267
 
3253
3268
  x0 : array_like, optional
3254
3269
  Initial state-vector. Defaults to zero.
@@ -3271,16 +3286,23 @@ def dstep(system, x0=None, t=None, n=None):
3271
3286
 
3272
3287
  Examples
3273
3288
  --------
3289
+ The following example illustrates how to create a digital Butterworth filer and
3290
+ plot its step response:
3291
+
3274
3292
  >>> import numpy as np
3275
3293
  >>> from scipy import signal
3276
3294
  >>> import matplotlib.pyplot as plt
3277
-
3278
- >>> butter = signal.dlti(*signal.butter(3, 0.5))
3279
- >>> t, y = signal.dstep(butter, n=25)
3280
- >>> plt.step(t, np.squeeze(y))
3281
- >>> plt.grid()
3282
- >>> plt.xlabel('n [samples]')
3283
- >>> plt.ylabel('Amplitude')
3295
+ ...
3296
+ >>> dt = 1 # sampling interval is one => time unit is sample number
3297
+ >>> bb, aa = signal.butter(3, 0.25, fs=1/dt)
3298
+ >>> t, y = signal.dstep((bb, aa, dt), n=25)
3299
+ ...
3300
+ >>> fig0, ax0 = plt.subplots()
3301
+ >>> ax0.step(t, np.squeeze(y), '.-', where='post')
3302
+ >>> ax0.set_title(r"Step Response of a $3^\text{rd}$ Order Butterworth Filter")
3303
+ >>> ax0.set(xlabel='Sample number', ylabel='Amplitude', ylim=(0, 1.1*np.max(y)))
3304
+ >>> ax0.grid()
3305
+ >>> plt.show()
3284
3306
  """
3285
3307
  # Convert system to dlti-StateSpace
3286
3308
  if isinstance(system, dlti):
@@ -3326,14 +3348,19 @@ def dfreqresp(system, w=None, n=10000, whole=False):
3326
3348
 
3327
3349
  Parameters
3328
3350
  ----------
3329
- system : an instance of the `dlti` class or a tuple describing the system.
3330
- The following gives the number of elements in the tuple and
3331
- the interpretation:
3332
-
3333
- * 1 (instance of `dlti`)
3334
- * 2 (numerator, denominator, dt)
3335
- * 3 (zeros, poles, gain, dt)
3336
- * 4 (A, B, C, D, dt)
3351
+ system : dlti | tuple
3352
+ An instance of the LTI class `dlti` or a tuple describing the system.
3353
+ The number of elements in the tuple determine the interpretation. I.e.:
3354
+
3355
+ * ``system``: Instance of LTI class `dlti`. Note that derived instances, such
3356
+ as instances of `TransferFunction`, `ZerosPolesGain`, or `StateSpace`, are
3357
+ allowed as well.
3358
+ * ``(num, den, dt)``: Rational polynomial as described in `TransferFunction`.
3359
+ The coefficients of the polynomials should be specified in descending
3360
+ exponent order, e.g., z² + 3z + 5 would be represented as ``[1, 3, 5]``.
3361
+ * ``(zeros, poles, gain, dt)``: Zeros, poles, gain form as described
3362
+ in `ZerosPolesGain`.
3363
+ * ``(A, B, C, D, dt)``: State-space form as described in `StateSpace`.
3337
3364
 
3338
3365
  w : array_like, optional
3339
3366
  Array of frequencies (in radians/sample). Magnitude and phase data is
@@ -3365,24 +3392,25 @@ def dfreqresp(system, w=None, n=10000, whole=False):
3365
3392
 
3366
3393
  Examples
3367
3394
  --------
3368
- Generating the Nyquist plot of a transfer function
3395
+ The following example generates the Nyquist plot of the transfer function
3396
+ :math:`H(z) = \frac{1}{z^2 + 2z + 3}` with a sampling time of 0.05 seconds:
3369
3397
 
3370
3398
  >>> from scipy import signal
3371
3399
  >>> import matplotlib.pyplot as plt
3372
-
3373
- Construct the transfer function
3374
- :math:`H(z) = \frac{1}{z^2 + 2z + 3}` with a sampling time of 0.05
3375
- seconds:
3376
-
3377
- >>> sys = signal.TransferFunction([1], [1, 2, 3], dt=0.05)
3378
-
3400
+ >>> sys = signal.TransferFunction([1], [1, 2, 3], dt=0.05) # construct H(z)
3379
3401
  >>> w, H = signal.dfreqresp(sys)
3380
-
3381
- >>> plt.figure()
3382
- >>> plt.plot(H.real, H.imag, "b")
3383
- >>> plt.plot(H.real, -H.imag, "r")
3402
+ ...
3403
+ >>> fig0, ax0 = plt.subplots()
3404
+ >>> ax0.plot(H.real, H.imag, label=r"$H(z=e^{+j\omega})$")
3405
+ >>> ax0.plot(H.real, -H.imag, label=r"$H(z=e^{-j\omega})$")
3406
+ >>> ax0.set_title(r"Nyquist Plot of $H(z) = 1 / (z^2 + 2z + 3)$")
3407
+ >>> ax0.set(xlabel=r"$\text{Re}\{z\}$", ylabel=r"$\text{Im}\{z\}$",
3408
+ ... xlim=(-0.2, 0.65), aspect='equal')
3409
+ >>> ax0.plot(H[0].real, H[0].imag, 'k.') # mark H(exp(1j*w[0]))
3410
+ >>> ax0.text(0.2, 0, r"$H(e^{j0})$")
3411
+ >>> ax0.grid(True)
3412
+ >>> ax0.legend()
3384
3413
  >>> plt.show()
3385
-
3386
3414
  """
3387
3415
  if not isinstance(system, dlti):
3388
3416
  if isinstance(system, lti):
@@ -3395,7 +3423,7 @@ def dfreqresp(system, w=None, n=10000, whole=False):
3395
3423
  # No SS->ZPK code exists right now, just SS->TF->ZPK
3396
3424
  system = system._as_tf()
3397
3425
 
3398
- if not isinstance(system, (TransferFunction, ZerosPolesGain)):
3426
+ if not isinstance(system, TransferFunction | ZerosPolesGain):
3399
3427
  raise ValueError('Unknown system type')
3400
3428
 
3401
3429
  if system.inputs != 1 or system.outputs != 1:
@@ -3421,24 +3449,23 @@ def dfreqresp(system, w=None, n=10000, whole=False):
3421
3449
 
3422
3450
 
3423
3451
  def dbode(system, w=None, n=100):
3424
- r"""
3425
- Calculate Bode magnitude and phase data of a discrete-time system.
3452
+ r"""Calculate Bode magnitude and phase data of a discrete-time system.
3426
3453
 
3427
3454
  Parameters
3428
3455
  ----------
3429
- system :
3456
+ system : dlti | tuple
3430
3457
  An instance of the LTI class `dlti` or a tuple describing the system.
3431
- The number of elements in the tuple determine the interpretation, i.e.:
3432
-
3433
- 1. ``(sys_dlti)``: Instance of LTI class `dlti`. Note that derived instances,
3434
- such as instances of `TransferFunction`, `ZerosPolesGain`, or `StateSpace`,
3435
- are allowed as well.
3436
- 2. ``(num, den, dt)``: Rational polynomial as described in `TransferFunction`.
3437
- The coefficients of the polynomials should be specified in descending
3438
- exponent order, e.g., z² + 3z + 5 would be represented as ``[1, 3, 5]``.
3439
- 3. ``(zeros, poles, gain, dt)``: Zeros, poles, gain form as described
3440
- in `ZerosPolesGain`.
3441
- 4. ``(A, B, C, D, dt)``: State-space form as described in `StateSpace`.
3458
+ The number of elements in the tuple determine the interpretation. I.e.:
3459
+
3460
+ * ``system``: Instance of LTI class `dlti`. Note that derived instances, such
3461
+ as instances of `TransferFunction`, `ZerosPolesGain`, or `StateSpace`, are
3462
+ allowed as well.
3463
+ * ``(num, den, dt)``: Rational polynomial as described in `TransferFunction`.
3464
+ The coefficients of the polynomials should be specified in descending
3465
+ exponent order, e.g., z² + 3z + 5 would be represented as ``[1, 3, 5]``.
3466
+ * ``(zeros, poles, gain, dt)``: Zeros, poles, gain form as described
3467
+ in `ZerosPolesGain`.
3468
+ * ``(A, B, C, D, dt)``: State-space form as described in `StateSpace`.
3442
3469
 
3443
3470
  w : array_like, optional
3444
3471
  Array of frequencies normalized to the Nyquist frequency being π, i.e.,
@@ -0,0 +1,172 @@
1
+ """Partial replacements for numpy polynomial routines, with Array API compatibility.
2
+
3
+ This module contains both "old-style", np.poly1d, routines from the main numpy
4
+ namespace, and "new-style", np.polynomial.polynomial, routines.
5
+
6
+ To distinguish the two sets, the "new-style" routine names start with `npp_`
7
+ """
8
+ import scipy._lib.array_api_extra as xpx
9
+ from scipy._lib._array_api import xp_promote, xp_default_dtype
10
+
11
+
12
+ def _sort_cmplx(arr, xp):
13
+ # xp.sort is undefined for complex dtypes. Here we only need some
14
+ # consistent way to sort a complex array, including equal magnitude elements.
15
+ arr = xp.asarray(arr)
16
+ if xp.isdtype(arr.dtype, 'complex floating'):
17
+ sorter = abs(arr) + xp.real(arr) + xp.imag(arr)**3
18
+ else:
19
+ sorter = arr
20
+
21
+ idxs = xp.argsort(sorter)
22
+ return arr[idxs]
23
+
24
+
25
+ def polyroots(coef, *, xp):
26
+ """numpy.roots, best-effor replacement
27
+ """
28
+ if coef.shape[0] < 2:
29
+ return xp.asarray([], dtype=coef.dtype)
30
+
31
+ root_func = getattr(xp, 'roots', None)
32
+ if root_func:
33
+ # NB: cupy.roots is broken in CuPy 13.x, but CuPy is handled via delegation
34
+ # so we never hit this code path with xp being cupy
35
+ return root_func(coef)
36
+
37
+ # companion matrix
38
+ n = coef.shape[0]
39
+ a = xp.eye(n - 1, n - 1, k=-1, dtype=coef.dtype)
40
+ a[:, -1] = -xp.flip(coef[1:]) / coef[0]
41
+
42
+ # non-symmetric eigenvalue problem is not in the spec but is available on e.g. torch
43
+ if hasattr(xp.linalg, 'eigvals'):
44
+ return xp.linalg.eigvals(a)
45
+ else:
46
+ import numpy as np
47
+ return xp.asarray(np.linalg.eigvals(np.asarray(a)))
48
+
49
+
50
+ # https://github.com/numpy/numpy/blob/v2.1.0/numpy/lib/_function_base_impl.py#L1874-L1925
51
+ def _trim_zeros(filt, trim='fb'):
52
+ first = 0
53
+ trim = trim.upper()
54
+ if 'F' in trim:
55
+ for i in filt:
56
+ if i != 0.:
57
+ break
58
+ else:
59
+ first = first + 1
60
+ last = filt.shape[0]
61
+ if 'B' in trim:
62
+ for i in filt[::-1]:
63
+ if i != 0.:
64
+ break
65
+ else:
66
+ last = last - 1
67
+ return filt[first:last]
68
+
69
+
70
+ # ### Old-style routines ###
71
+
72
+
73
+ # https://github.com/numpy/numpy/blob/v2.2.0/numpy/lib/_polynomial_impl.py#L1232
74
+ def _poly1d(c_or_r, *, xp):
75
+ """ Constructor of np.poly1d object from an array of coefficients (r=False)
76
+ """
77
+ c_or_r = xpx.atleast_nd(c_or_r, ndim=1, xp=xp)
78
+ if c_or_r.ndim > 1:
79
+ raise ValueError("Polynomial must be 1d only.")
80
+ c_or_r = _trim_zeros(c_or_r, trim='f')
81
+ if c_or_r.shape[0] == 0:
82
+ c_or_r = xp.asarray([0], dtype=c_or_r.dtype)
83
+ return c_or_r
84
+
85
+
86
+ # https://github.com/numpy/numpy/blob/v2.2.0/numpy/lib/_polynomial_impl.py#L702-L779
87
+ def polyval(p, x, *, xp):
88
+ """ Old-style polynomial, `np.polyval`
89
+ """
90
+ y = xp.zeros_like(x)
91
+
92
+ for pv in p:
93
+ y = y * x + pv
94
+ return y
95
+
96
+
97
+ # https://github.com/numpy/numpy/blob/v2.2.0/numpy/lib/_polynomial_impl.py#L34-L157
98
+ def poly(seq_of_zeros, *, xp):
99
+ # Only reproduce the 1D variant of np.poly
100
+ seq_of_zeros = xp.asarray(seq_of_zeros)
101
+ seq_of_zeros = xpx.atleast_nd(seq_of_zeros, ndim=1, xp=xp)
102
+
103
+ if seq_of_zeros.shape[0] == 0:
104
+ return 1.0
105
+
106
+ # prefer np.convolve etc, if available
107
+ convolve_func = getattr(xp, 'convolve', None)
108
+ if convolve_func is None:
109
+ from scipy.signal import convolve as convolve_func
110
+
111
+ dt = seq_of_zeros.dtype
112
+ a = xp.ones((1,), dtype=dt)
113
+ one = xp.ones_like(seq_of_zeros[0])
114
+ for zero in seq_of_zeros:
115
+ a = convolve_func(a, xp.stack((one, -zero)), mode='full')
116
+
117
+ if xp.isdtype(a.dtype, 'complex floating'):
118
+ # if complex roots are all complex conjugates, the roots are real.
119
+ roots = xp.asarray(seq_of_zeros, dtype=xp.complex128)
120
+ if xp.all(_sort_cmplx(roots, xp) == _sort_cmplx(xp.conj(roots), xp)):
121
+ a = xp.asarray(xp.real(a), copy=True)
122
+
123
+ return a
124
+
125
+
126
+ # https://github.com/numpy/numpy/blob/v2.2.0/numpy/lib/_polynomial_impl.py#L912
127
+ def polymul(a1, a2, *, xp):
128
+ a1, a2 = _poly1d(a1, xp=xp), _poly1d(a2, xp=xp)
129
+
130
+ # prefer np.convolve etc, if available
131
+ convolve_func = getattr(xp, 'convolve', None)
132
+ if convolve_func is None:
133
+ from scipy.signal import convolve as convolve_func
134
+
135
+ val = convolve_func(a1, a2)
136
+ return val
137
+
138
+
139
+ # ### New-style routines ###
140
+
141
+
142
+ # https://github.com/numpy/numpy/blob/v2.2.0/numpy/polynomial/polynomial.py#L663
143
+ def npp_polyval(x, c, *, xp, tensor=True):
144
+ if xp.isdtype(c.dtype, 'integral'):
145
+ c = xp.astype(c, xp_default_dtype(xp))
146
+
147
+ c = xpx.atleast_nd(c, ndim=1, xp=xp)
148
+ if isinstance(x, tuple | list):
149
+ x = xp.asarray(x)
150
+ if tensor:
151
+ c = xp.reshape(c, (c.shape + (1,)*x.ndim))
152
+
153
+ c0, _ = xp_promote(c[-1, ...], x, broadcast=True, xp=xp)
154
+ for i in range(2, c.shape[0] + 1):
155
+ c0 = c[-i, ...] + c0*x
156
+ return c0
157
+
158
+
159
+ # https://github.com/numpy/numpy/blob/v2.2.0/numpy/polynomial/polynomial.py#L758-L842
160
+ def npp_polyvalfromroots(x, r, *, xp, tensor=True):
161
+ r = xpx.atleast_nd(r, ndim=1, xp=xp)
162
+ # if r.dtype.char in '?bBhHiIlLqQpP':
163
+ # r = r.astype(np.double)
164
+
165
+ if isinstance(x, tuple | list):
166
+ x = xp.asarray(x)
167
+
168
+ if tensor:
169
+ r = xp.reshape(r, r.shape + (1,) * x.ndim)
170
+ elif x.ndim >= r.ndim:
171
+ raise ValueError("x.ndim must be < r.ndim when tensor == False")
172
+ return xp.prod(x - r, axis=0)