numpy 2.4.1__pp311-pypy311_pp73-macosx_14_0_arm64.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 (1039) hide show
  1. numpy/__config__.py +170 -0
  2. numpy/__config__.pyi +108 -0
  3. numpy/__init__.cython-30.pxd +1242 -0
  4. numpy/__init__.pxd +1155 -0
  5. numpy/__init__.py +942 -0
  6. numpy/__init__.pyi +6202 -0
  7. numpy/_array_api_info.py +346 -0
  8. numpy/_array_api_info.pyi +206 -0
  9. numpy/_configtool.py +39 -0
  10. numpy/_configtool.pyi +1 -0
  11. numpy/_core/__init__.py +201 -0
  12. numpy/_core/__init__.pyi +666 -0
  13. numpy/_core/_add_newdocs.py +7151 -0
  14. numpy/_core/_add_newdocs.pyi +2 -0
  15. numpy/_core/_add_newdocs_scalars.py +381 -0
  16. numpy/_core/_add_newdocs_scalars.pyi +16 -0
  17. numpy/_core/_asarray.py +130 -0
  18. numpy/_core/_asarray.pyi +43 -0
  19. numpy/_core/_dtype.py +366 -0
  20. numpy/_core/_dtype.pyi +56 -0
  21. numpy/_core/_dtype_ctypes.py +120 -0
  22. numpy/_core/_dtype_ctypes.pyi +83 -0
  23. numpy/_core/_exceptions.py +162 -0
  24. numpy/_core/_exceptions.pyi +54 -0
  25. numpy/_core/_internal.py +968 -0
  26. numpy/_core/_internal.pyi +61 -0
  27. numpy/_core/_methods.py +252 -0
  28. numpy/_core/_methods.pyi +22 -0
  29. numpy/_core/_multiarray_tests.pypy311-pp73-darwin.so +0 -0
  30. numpy/_core/_multiarray_umath.pypy311-pp73-darwin.so +0 -0
  31. numpy/_core/_operand_flag_tests.pypy311-pp73-darwin.so +0 -0
  32. numpy/_core/_rational_tests.pypy311-pp73-darwin.so +0 -0
  33. numpy/_core/_simd.pyi +35 -0
  34. numpy/_core/_simd.pypy311-pp73-darwin.so +0 -0
  35. numpy/_core/_string_helpers.py +100 -0
  36. numpy/_core/_string_helpers.pyi +12 -0
  37. numpy/_core/_struct_ufunc_tests.pypy311-pp73-darwin.so +0 -0
  38. numpy/_core/_type_aliases.py +131 -0
  39. numpy/_core/_type_aliases.pyi +86 -0
  40. numpy/_core/_ufunc_config.py +515 -0
  41. numpy/_core/_ufunc_config.pyi +69 -0
  42. numpy/_core/_umath_tests.pyi +47 -0
  43. numpy/_core/_umath_tests.pypy311-pp73-darwin.so +0 -0
  44. numpy/_core/arrayprint.py +1779 -0
  45. numpy/_core/arrayprint.pyi +158 -0
  46. numpy/_core/cversions.py +13 -0
  47. numpy/_core/defchararray.py +1414 -0
  48. numpy/_core/defchararray.pyi +1150 -0
  49. numpy/_core/einsumfunc.py +1650 -0
  50. numpy/_core/einsumfunc.pyi +184 -0
  51. numpy/_core/fromnumeric.py +4233 -0
  52. numpy/_core/fromnumeric.pyi +1735 -0
  53. numpy/_core/function_base.py +547 -0
  54. numpy/_core/function_base.pyi +276 -0
  55. numpy/_core/getlimits.py +462 -0
  56. numpy/_core/getlimits.pyi +124 -0
  57. numpy/_core/include/numpy/__multiarray_api.c +376 -0
  58. numpy/_core/include/numpy/__multiarray_api.h +1628 -0
  59. numpy/_core/include/numpy/__ufunc_api.c +55 -0
  60. numpy/_core/include/numpy/__ufunc_api.h +349 -0
  61. numpy/_core/include/numpy/_neighborhood_iterator_imp.h +90 -0
  62. numpy/_core/include/numpy/_numpyconfig.h +33 -0
  63. numpy/_core/include/numpy/_public_dtype_api_table.h +86 -0
  64. numpy/_core/include/numpy/arrayobject.h +7 -0
  65. numpy/_core/include/numpy/arrayscalars.h +198 -0
  66. numpy/_core/include/numpy/dtype_api.h +547 -0
  67. numpy/_core/include/numpy/halffloat.h +70 -0
  68. numpy/_core/include/numpy/ndarrayobject.h +304 -0
  69. numpy/_core/include/numpy/ndarraytypes.h +1982 -0
  70. numpy/_core/include/numpy/npy_2_compat.h +249 -0
  71. numpy/_core/include/numpy/npy_2_complexcompat.h +28 -0
  72. numpy/_core/include/numpy/npy_3kcompat.h +374 -0
  73. numpy/_core/include/numpy/npy_common.h +989 -0
  74. numpy/_core/include/numpy/npy_cpu.h +126 -0
  75. numpy/_core/include/numpy/npy_endian.h +79 -0
  76. numpy/_core/include/numpy/npy_math.h +602 -0
  77. numpy/_core/include/numpy/npy_no_deprecated_api.h +20 -0
  78. numpy/_core/include/numpy/npy_os.h +42 -0
  79. numpy/_core/include/numpy/numpyconfig.h +185 -0
  80. numpy/_core/include/numpy/random/LICENSE.txt +21 -0
  81. numpy/_core/include/numpy/random/bitgen.h +20 -0
  82. numpy/_core/include/numpy/random/distributions.h +209 -0
  83. numpy/_core/include/numpy/random/libdivide.h +2079 -0
  84. numpy/_core/include/numpy/ufuncobject.h +343 -0
  85. numpy/_core/include/numpy/utils.h +37 -0
  86. numpy/_core/lib/libnpymath.a +0 -0
  87. numpy/_core/lib/npy-pkg-config/mlib.ini +12 -0
  88. numpy/_core/lib/npy-pkg-config/npymath.ini +20 -0
  89. numpy/_core/lib/pkgconfig/numpy.pc +7 -0
  90. numpy/_core/memmap.py +363 -0
  91. numpy/_core/memmap.pyi +3 -0
  92. numpy/_core/multiarray.py +1740 -0
  93. numpy/_core/multiarray.pyi +1316 -0
  94. numpy/_core/numeric.py +2758 -0
  95. numpy/_core/numeric.pyi +1276 -0
  96. numpy/_core/numerictypes.py +633 -0
  97. numpy/_core/numerictypes.pyi +196 -0
  98. numpy/_core/overrides.py +188 -0
  99. numpy/_core/overrides.pyi +47 -0
  100. numpy/_core/printoptions.py +32 -0
  101. numpy/_core/printoptions.pyi +28 -0
  102. numpy/_core/records.py +1088 -0
  103. numpy/_core/records.pyi +340 -0
  104. numpy/_core/shape_base.py +996 -0
  105. numpy/_core/shape_base.pyi +182 -0
  106. numpy/_core/strings.py +1813 -0
  107. numpy/_core/strings.pyi +536 -0
  108. numpy/_core/tests/_locales.py +72 -0
  109. numpy/_core/tests/_natype.py +144 -0
  110. numpy/_core/tests/data/astype_copy.pkl +0 -0
  111. numpy/_core/tests/data/generate_umath_validation_data.cpp +170 -0
  112. numpy/_core/tests/data/recarray_from_file.fits +0 -0
  113. numpy/_core/tests/data/umath-validation-set-README.txt +15 -0
  114. numpy/_core/tests/data/umath-validation-set-arccos.csv +1429 -0
  115. numpy/_core/tests/data/umath-validation-set-arccosh.csv +1429 -0
  116. numpy/_core/tests/data/umath-validation-set-arcsin.csv +1429 -0
  117. numpy/_core/tests/data/umath-validation-set-arcsinh.csv +1429 -0
  118. numpy/_core/tests/data/umath-validation-set-arctan.csv +1429 -0
  119. numpy/_core/tests/data/umath-validation-set-arctanh.csv +1429 -0
  120. numpy/_core/tests/data/umath-validation-set-cbrt.csv +1429 -0
  121. numpy/_core/tests/data/umath-validation-set-cos.csv +1375 -0
  122. numpy/_core/tests/data/umath-validation-set-cosh.csv +1429 -0
  123. numpy/_core/tests/data/umath-validation-set-exp.csv +412 -0
  124. numpy/_core/tests/data/umath-validation-set-exp2.csv +1429 -0
  125. numpy/_core/tests/data/umath-validation-set-expm1.csv +1429 -0
  126. numpy/_core/tests/data/umath-validation-set-log.csv +271 -0
  127. numpy/_core/tests/data/umath-validation-set-log10.csv +1629 -0
  128. numpy/_core/tests/data/umath-validation-set-log1p.csv +1429 -0
  129. numpy/_core/tests/data/umath-validation-set-log2.csv +1629 -0
  130. numpy/_core/tests/data/umath-validation-set-sin.csv +1370 -0
  131. numpy/_core/tests/data/umath-validation-set-sinh.csv +1429 -0
  132. numpy/_core/tests/data/umath-validation-set-tan.csv +1429 -0
  133. numpy/_core/tests/data/umath-validation-set-tanh.csv +1429 -0
  134. numpy/_core/tests/examples/cython/checks.pyx +373 -0
  135. numpy/_core/tests/examples/cython/meson.build +43 -0
  136. numpy/_core/tests/examples/cython/setup.py +39 -0
  137. numpy/_core/tests/examples/limited_api/limited_api1.c +17 -0
  138. numpy/_core/tests/examples/limited_api/limited_api2.pyx +11 -0
  139. numpy/_core/tests/examples/limited_api/limited_api_latest.c +19 -0
  140. numpy/_core/tests/examples/limited_api/meson.build +59 -0
  141. numpy/_core/tests/examples/limited_api/setup.py +24 -0
  142. numpy/_core/tests/test__exceptions.py +90 -0
  143. numpy/_core/tests/test_abc.py +54 -0
  144. numpy/_core/tests/test_api.py +655 -0
  145. numpy/_core/tests/test_argparse.py +90 -0
  146. numpy/_core/tests/test_array_api_info.py +113 -0
  147. numpy/_core/tests/test_array_coercion.py +928 -0
  148. numpy/_core/tests/test_array_interface.py +222 -0
  149. numpy/_core/tests/test_arraymethod.py +84 -0
  150. numpy/_core/tests/test_arrayobject.py +75 -0
  151. numpy/_core/tests/test_arrayprint.py +1324 -0
  152. numpy/_core/tests/test_casting_floatingpoint_errors.py +154 -0
  153. numpy/_core/tests/test_casting_unittests.py +955 -0
  154. numpy/_core/tests/test_conversion_utils.py +209 -0
  155. numpy/_core/tests/test_cpu_dispatcher.py +48 -0
  156. numpy/_core/tests/test_cpu_features.py +450 -0
  157. numpy/_core/tests/test_custom_dtypes.py +393 -0
  158. numpy/_core/tests/test_cython.py +352 -0
  159. numpy/_core/tests/test_datetime.py +2792 -0
  160. numpy/_core/tests/test_defchararray.py +858 -0
  161. numpy/_core/tests/test_deprecations.py +460 -0
  162. numpy/_core/tests/test_dlpack.py +190 -0
  163. numpy/_core/tests/test_dtype.py +2110 -0
  164. numpy/_core/tests/test_einsum.py +1351 -0
  165. numpy/_core/tests/test_errstate.py +131 -0
  166. numpy/_core/tests/test_extint128.py +217 -0
  167. numpy/_core/tests/test_finfo.py +86 -0
  168. numpy/_core/tests/test_function_base.py +504 -0
  169. numpy/_core/tests/test_getlimits.py +171 -0
  170. numpy/_core/tests/test_half.py +593 -0
  171. numpy/_core/tests/test_hashtable.py +36 -0
  172. numpy/_core/tests/test_indexerrors.py +122 -0
  173. numpy/_core/tests/test_indexing.py +1692 -0
  174. numpy/_core/tests/test_item_selection.py +167 -0
  175. numpy/_core/tests/test_limited_api.py +102 -0
  176. numpy/_core/tests/test_longdouble.py +370 -0
  177. numpy/_core/tests/test_mem_overlap.py +933 -0
  178. numpy/_core/tests/test_mem_policy.py +453 -0
  179. numpy/_core/tests/test_memmap.py +248 -0
  180. numpy/_core/tests/test_multiarray.py +11008 -0
  181. numpy/_core/tests/test_multiprocessing.py +55 -0
  182. numpy/_core/tests/test_multithreading.py +377 -0
  183. numpy/_core/tests/test_nditer.py +3533 -0
  184. numpy/_core/tests/test_nep50_promotions.py +287 -0
  185. numpy/_core/tests/test_numeric.py +4295 -0
  186. numpy/_core/tests/test_numerictypes.py +650 -0
  187. numpy/_core/tests/test_overrides.py +800 -0
  188. numpy/_core/tests/test_print.py +202 -0
  189. numpy/_core/tests/test_protocols.py +46 -0
  190. numpy/_core/tests/test_records.py +544 -0
  191. numpy/_core/tests/test_regression.py +2677 -0
  192. numpy/_core/tests/test_scalar_ctors.py +203 -0
  193. numpy/_core/tests/test_scalar_methods.py +328 -0
  194. numpy/_core/tests/test_scalarbuffer.py +153 -0
  195. numpy/_core/tests/test_scalarinherit.py +105 -0
  196. numpy/_core/tests/test_scalarmath.py +1168 -0
  197. numpy/_core/tests/test_scalarprint.py +403 -0
  198. numpy/_core/tests/test_shape_base.py +904 -0
  199. numpy/_core/tests/test_simd.py +1345 -0
  200. numpy/_core/tests/test_simd_module.py +105 -0
  201. numpy/_core/tests/test_stringdtype.py +1855 -0
  202. numpy/_core/tests/test_strings.py +1523 -0
  203. numpy/_core/tests/test_ufunc.py +3405 -0
  204. numpy/_core/tests/test_umath.py +4962 -0
  205. numpy/_core/tests/test_umath_accuracy.py +132 -0
  206. numpy/_core/tests/test_umath_complex.py +631 -0
  207. numpy/_core/tests/test_unicode.py +369 -0
  208. numpy/_core/umath.py +60 -0
  209. numpy/_core/umath.pyi +232 -0
  210. numpy/_distributor_init.py +15 -0
  211. numpy/_distributor_init.pyi +1 -0
  212. numpy/_expired_attrs_2_0.py +78 -0
  213. numpy/_expired_attrs_2_0.pyi +61 -0
  214. numpy/_globals.py +121 -0
  215. numpy/_globals.pyi +17 -0
  216. numpy/_pyinstaller/__init__.py +0 -0
  217. numpy/_pyinstaller/__init__.pyi +0 -0
  218. numpy/_pyinstaller/hook-numpy.py +36 -0
  219. numpy/_pyinstaller/hook-numpy.pyi +6 -0
  220. numpy/_pyinstaller/tests/__init__.py +16 -0
  221. numpy/_pyinstaller/tests/pyinstaller-smoke.py +32 -0
  222. numpy/_pyinstaller/tests/test_pyinstaller.py +35 -0
  223. numpy/_pytesttester.py +201 -0
  224. numpy/_pytesttester.pyi +18 -0
  225. numpy/_typing/__init__.py +173 -0
  226. numpy/_typing/_add_docstring.py +153 -0
  227. numpy/_typing/_array_like.py +106 -0
  228. numpy/_typing/_char_codes.py +213 -0
  229. numpy/_typing/_dtype_like.py +114 -0
  230. numpy/_typing/_extended_precision.py +15 -0
  231. numpy/_typing/_nbit.py +19 -0
  232. numpy/_typing/_nbit_base.py +94 -0
  233. numpy/_typing/_nbit_base.pyi +39 -0
  234. numpy/_typing/_nested_sequence.py +79 -0
  235. numpy/_typing/_scalars.py +20 -0
  236. numpy/_typing/_shape.py +8 -0
  237. numpy/_typing/_ufunc.py +7 -0
  238. numpy/_typing/_ufunc.pyi +975 -0
  239. numpy/_utils/__init__.py +95 -0
  240. numpy/_utils/__init__.pyi +28 -0
  241. numpy/_utils/_convertions.py +18 -0
  242. numpy/_utils/_convertions.pyi +4 -0
  243. numpy/_utils/_inspect.py +192 -0
  244. numpy/_utils/_inspect.pyi +70 -0
  245. numpy/_utils/_pep440.py +486 -0
  246. numpy/_utils/_pep440.pyi +118 -0
  247. numpy/char/__init__.py +2 -0
  248. numpy/char/__init__.pyi +111 -0
  249. numpy/conftest.py +248 -0
  250. numpy/core/__init__.py +33 -0
  251. numpy/core/__init__.pyi +0 -0
  252. numpy/core/_dtype.py +10 -0
  253. numpy/core/_dtype.pyi +0 -0
  254. numpy/core/_dtype_ctypes.py +10 -0
  255. numpy/core/_dtype_ctypes.pyi +0 -0
  256. numpy/core/_internal.py +27 -0
  257. numpy/core/_multiarray_umath.py +57 -0
  258. numpy/core/_utils.py +21 -0
  259. numpy/core/arrayprint.py +10 -0
  260. numpy/core/defchararray.py +10 -0
  261. numpy/core/einsumfunc.py +10 -0
  262. numpy/core/fromnumeric.py +10 -0
  263. numpy/core/function_base.py +10 -0
  264. numpy/core/getlimits.py +10 -0
  265. numpy/core/multiarray.py +25 -0
  266. numpy/core/numeric.py +12 -0
  267. numpy/core/numerictypes.py +10 -0
  268. numpy/core/overrides.py +10 -0
  269. numpy/core/overrides.pyi +7 -0
  270. numpy/core/records.py +10 -0
  271. numpy/core/shape_base.py +10 -0
  272. numpy/core/umath.py +10 -0
  273. numpy/ctypeslib/__init__.py +13 -0
  274. numpy/ctypeslib/__init__.pyi +15 -0
  275. numpy/ctypeslib/_ctypeslib.py +603 -0
  276. numpy/ctypeslib/_ctypeslib.pyi +236 -0
  277. numpy/distutils/__init__.py +64 -0
  278. numpy/distutils/__init__.pyi +4 -0
  279. numpy/distutils/__pycache__/conv_template.pypy311.pyc +0 -0
  280. numpy/distutils/_shell_utils.py +87 -0
  281. numpy/distutils/armccompiler.py +26 -0
  282. numpy/distutils/ccompiler.py +826 -0
  283. numpy/distutils/ccompiler_opt.py +2668 -0
  284. numpy/distutils/checks/cpu_asimd.c +27 -0
  285. numpy/distutils/checks/cpu_asimddp.c +16 -0
  286. numpy/distutils/checks/cpu_asimdfhm.c +19 -0
  287. numpy/distutils/checks/cpu_asimdhp.c +15 -0
  288. numpy/distutils/checks/cpu_avx.c +20 -0
  289. numpy/distutils/checks/cpu_avx2.c +20 -0
  290. numpy/distutils/checks/cpu_avx512_clx.c +22 -0
  291. numpy/distutils/checks/cpu_avx512_cnl.c +24 -0
  292. numpy/distutils/checks/cpu_avx512_icl.c +26 -0
  293. numpy/distutils/checks/cpu_avx512_knl.c +25 -0
  294. numpy/distutils/checks/cpu_avx512_knm.c +30 -0
  295. numpy/distutils/checks/cpu_avx512_skx.c +26 -0
  296. numpy/distutils/checks/cpu_avx512_spr.c +26 -0
  297. numpy/distutils/checks/cpu_avx512cd.c +20 -0
  298. numpy/distutils/checks/cpu_avx512f.c +20 -0
  299. numpy/distutils/checks/cpu_f16c.c +22 -0
  300. numpy/distutils/checks/cpu_fma3.c +22 -0
  301. numpy/distutils/checks/cpu_fma4.c +13 -0
  302. numpy/distutils/checks/cpu_lsx.c +11 -0
  303. numpy/distutils/checks/cpu_neon.c +19 -0
  304. numpy/distutils/checks/cpu_neon_fp16.c +11 -0
  305. numpy/distutils/checks/cpu_neon_vfpv4.c +21 -0
  306. numpy/distutils/checks/cpu_popcnt.c +32 -0
  307. numpy/distutils/checks/cpu_rvv.c +13 -0
  308. numpy/distutils/checks/cpu_sse.c +20 -0
  309. numpy/distutils/checks/cpu_sse2.c +20 -0
  310. numpy/distutils/checks/cpu_sse3.c +20 -0
  311. numpy/distutils/checks/cpu_sse41.c +20 -0
  312. numpy/distutils/checks/cpu_sse42.c +20 -0
  313. numpy/distutils/checks/cpu_ssse3.c +20 -0
  314. numpy/distutils/checks/cpu_sve.c +14 -0
  315. numpy/distutils/checks/cpu_vsx.c +21 -0
  316. numpy/distutils/checks/cpu_vsx2.c +13 -0
  317. numpy/distutils/checks/cpu_vsx3.c +13 -0
  318. numpy/distutils/checks/cpu_vsx4.c +14 -0
  319. numpy/distutils/checks/cpu_vx.c +16 -0
  320. numpy/distutils/checks/cpu_vxe.c +25 -0
  321. numpy/distutils/checks/cpu_vxe2.c +21 -0
  322. numpy/distutils/checks/cpu_xop.c +12 -0
  323. numpy/distutils/checks/extra_avx512bw_mask.c +18 -0
  324. numpy/distutils/checks/extra_avx512dq_mask.c +16 -0
  325. numpy/distutils/checks/extra_avx512f_reduce.c +41 -0
  326. numpy/distutils/checks/extra_vsx3_half_double.c +12 -0
  327. numpy/distutils/checks/extra_vsx4_mma.c +21 -0
  328. numpy/distutils/checks/extra_vsx_asm.c +36 -0
  329. numpy/distutils/checks/test_flags.c +1 -0
  330. numpy/distutils/command/__init__.py +41 -0
  331. numpy/distutils/command/autodist.py +148 -0
  332. numpy/distutils/command/bdist_rpm.py +22 -0
  333. numpy/distutils/command/build.py +62 -0
  334. numpy/distutils/command/build_clib.py +469 -0
  335. numpy/distutils/command/build_ext.py +752 -0
  336. numpy/distutils/command/build_py.py +31 -0
  337. numpy/distutils/command/build_scripts.py +49 -0
  338. numpy/distutils/command/build_src.py +773 -0
  339. numpy/distutils/command/config.py +516 -0
  340. numpy/distutils/command/config_compiler.py +126 -0
  341. numpy/distutils/command/develop.py +15 -0
  342. numpy/distutils/command/egg_info.py +25 -0
  343. numpy/distutils/command/install.py +79 -0
  344. numpy/distutils/command/install_clib.py +40 -0
  345. numpy/distutils/command/install_data.py +24 -0
  346. numpy/distutils/command/install_headers.py +25 -0
  347. numpy/distutils/command/sdist.py +27 -0
  348. numpy/distutils/conv_template.py +329 -0
  349. numpy/distutils/core.py +215 -0
  350. numpy/distutils/cpuinfo.py +683 -0
  351. numpy/distutils/exec_command.py +315 -0
  352. numpy/distutils/extension.py +101 -0
  353. numpy/distutils/fcompiler/__init__.py +1035 -0
  354. numpy/distutils/fcompiler/absoft.py +158 -0
  355. numpy/distutils/fcompiler/arm.py +71 -0
  356. numpy/distutils/fcompiler/compaq.py +120 -0
  357. numpy/distutils/fcompiler/environment.py +88 -0
  358. numpy/distutils/fcompiler/fujitsu.py +46 -0
  359. numpy/distutils/fcompiler/g95.py +42 -0
  360. numpy/distutils/fcompiler/gnu.py +555 -0
  361. numpy/distutils/fcompiler/hpux.py +41 -0
  362. numpy/distutils/fcompiler/ibm.py +97 -0
  363. numpy/distutils/fcompiler/intel.py +211 -0
  364. numpy/distutils/fcompiler/lahey.py +45 -0
  365. numpy/distutils/fcompiler/mips.py +54 -0
  366. numpy/distutils/fcompiler/nag.py +87 -0
  367. numpy/distutils/fcompiler/none.py +28 -0
  368. numpy/distutils/fcompiler/nv.py +53 -0
  369. numpy/distutils/fcompiler/pathf95.py +33 -0
  370. numpy/distutils/fcompiler/pg.py +128 -0
  371. numpy/distutils/fcompiler/sun.py +51 -0
  372. numpy/distutils/fcompiler/vast.py +52 -0
  373. numpy/distutils/from_template.py +261 -0
  374. numpy/distutils/fujitsuccompiler.py +28 -0
  375. numpy/distutils/intelccompiler.py +106 -0
  376. numpy/distutils/lib2def.py +116 -0
  377. numpy/distutils/line_endings.py +77 -0
  378. numpy/distutils/log.py +111 -0
  379. numpy/distutils/mingw/gfortran_vs2003_hack.c +6 -0
  380. numpy/distutils/mingw32ccompiler.py +620 -0
  381. numpy/distutils/misc_util.py +2484 -0
  382. numpy/distutils/msvc9compiler.py +63 -0
  383. numpy/distutils/msvccompiler.py +76 -0
  384. numpy/distutils/npy_pkg_config.py +441 -0
  385. numpy/distutils/numpy_distribution.py +17 -0
  386. numpy/distutils/pathccompiler.py +21 -0
  387. numpy/distutils/system_info.py +3267 -0
  388. numpy/distutils/tests/__init__.py +0 -0
  389. numpy/distutils/tests/test_build_ext.py +74 -0
  390. numpy/distutils/tests/test_ccompiler_opt.py +808 -0
  391. numpy/distutils/tests/test_ccompiler_opt_conf.py +176 -0
  392. numpy/distutils/tests/test_exec_command.py +217 -0
  393. numpy/distutils/tests/test_fcompiler.py +43 -0
  394. numpy/distutils/tests/test_fcompiler_gnu.py +55 -0
  395. numpy/distutils/tests/test_fcompiler_intel.py +30 -0
  396. numpy/distutils/tests/test_fcompiler_nagfor.py +22 -0
  397. numpy/distutils/tests/test_from_template.py +44 -0
  398. numpy/distutils/tests/test_log.py +34 -0
  399. numpy/distutils/tests/test_mingw32ccompiler.py +47 -0
  400. numpy/distutils/tests/test_misc_util.py +88 -0
  401. numpy/distutils/tests/test_npy_pkg_config.py +84 -0
  402. numpy/distutils/tests/test_shell_utils.py +79 -0
  403. numpy/distutils/tests/test_system_info.py +334 -0
  404. numpy/distutils/tests/utilities.py +90 -0
  405. numpy/distutils/unixccompiler.py +141 -0
  406. numpy/doc/ufuncs.py +138 -0
  407. numpy/dtypes.py +41 -0
  408. numpy/dtypes.pyi +630 -0
  409. numpy/exceptions.py +246 -0
  410. numpy/exceptions.pyi +27 -0
  411. numpy/f2py/__init__.py +86 -0
  412. numpy/f2py/__init__.pyi +5 -0
  413. numpy/f2py/__main__.py +5 -0
  414. numpy/f2py/__version__.py +1 -0
  415. numpy/f2py/__version__.pyi +1 -0
  416. numpy/f2py/_backends/__init__.py +9 -0
  417. numpy/f2py/_backends/__init__.pyi +5 -0
  418. numpy/f2py/_backends/_backend.py +44 -0
  419. numpy/f2py/_backends/_backend.pyi +46 -0
  420. numpy/f2py/_backends/_distutils.py +76 -0
  421. numpy/f2py/_backends/_distutils.pyi +13 -0
  422. numpy/f2py/_backends/_meson.py +244 -0
  423. numpy/f2py/_backends/_meson.pyi +62 -0
  424. numpy/f2py/_backends/meson.build.template +58 -0
  425. numpy/f2py/_isocbind.py +62 -0
  426. numpy/f2py/_isocbind.pyi +13 -0
  427. numpy/f2py/_src_pyf.py +247 -0
  428. numpy/f2py/_src_pyf.pyi +28 -0
  429. numpy/f2py/auxfuncs.py +1004 -0
  430. numpy/f2py/auxfuncs.pyi +262 -0
  431. numpy/f2py/capi_maps.py +811 -0
  432. numpy/f2py/capi_maps.pyi +33 -0
  433. numpy/f2py/cb_rules.py +665 -0
  434. numpy/f2py/cb_rules.pyi +17 -0
  435. numpy/f2py/cfuncs.py +1563 -0
  436. numpy/f2py/cfuncs.pyi +31 -0
  437. numpy/f2py/common_rules.py +143 -0
  438. numpy/f2py/common_rules.pyi +9 -0
  439. numpy/f2py/crackfortran.py +3725 -0
  440. numpy/f2py/crackfortran.pyi +266 -0
  441. numpy/f2py/diagnose.py +149 -0
  442. numpy/f2py/diagnose.pyi +1 -0
  443. numpy/f2py/f2py2e.py +788 -0
  444. numpy/f2py/f2py2e.pyi +74 -0
  445. numpy/f2py/f90mod_rules.py +269 -0
  446. numpy/f2py/f90mod_rules.pyi +16 -0
  447. numpy/f2py/func2subr.py +329 -0
  448. numpy/f2py/func2subr.pyi +7 -0
  449. numpy/f2py/rules.py +1629 -0
  450. numpy/f2py/rules.pyi +41 -0
  451. numpy/f2py/setup.cfg +3 -0
  452. numpy/f2py/src/fortranobject.c +1436 -0
  453. numpy/f2py/src/fortranobject.h +173 -0
  454. numpy/f2py/symbolic.py +1518 -0
  455. numpy/f2py/symbolic.pyi +219 -0
  456. numpy/f2py/tests/__init__.py +16 -0
  457. numpy/f2py/tests/src/abstract_interface/foo.f90 +34 -0
  458. numpy/f2py/tests/src/abstract_interface/gh18403_mod.f90 +6 -0
  459. numpy/f2py/tests/src/array_from_pyobj/wrapmodule.c +235 -0
  460. numpy/f2py/tests/src/assumed_shape/.f2py_f2cmap +1 -0
  461. numpy/f2py/tests/src/assumed_shape/foo_free.f90 +34 -0
  462. numpy/f2py/tests/src/assumed_shape/foo_mod.f90 +41 -0
  463. numpy/f2py/tests/src/assumed_shape/foo_use.f90 +19 -0
  464. numpy/f2py/tests/src/assumed_shape/precision.f90 +4 -0
  465. numpy/f2py/tests/src/block_docstring/foo.f +6 -0
  466. numpy/f2py/tests/src/callback/foo.f +62 -0
  467. numpy/f2py/tests/src/callback/gh17797.f90 +7 -0
  468. numpy/f2py/tests/src/callback/gh18335.f90 +17 -0
  469. numpy/f2py/tests/src/callback/gh25211.f +10 -0
  470. numpy/f2py/tests/src/callback/gh25211.pyf +18 -0
  471. numpy/f2py/tests/src/callback/gh26681.f90 +18 -0
  472. numpy/f2py/tests/src/cli/gh_22819.pyf +6 -0
  473. numpy/f2py/tests/src/cli/hi77.f +3 -0
  474. numpy/f2py/tests/src/cli/hiworld.f90 +3 -0
  475. numpy/f2py/tests/src/common/block.f +11 -0
  476. numpy/f2py/tests/src/common/gh19161.f90 +10 -0
  477. numpy/f2py/tests/src/crackfortran/accesstype.f90 +13 -0
  478. numpy/f2py/tests/src/crackfortran/common_with_division.f +17 -0
  479. numpy/f2py/tests/src/crackfortran/data_common.f +8 -0
  480. numpy/f2py/tests/src/crackfortran/data_multiplier.f +5 -0
  481. numpy/f2py/tests/src/crackfortran/data_stmts.f90 +20 -0
  482. numpy/f2py/tests/src/crackfortran/data_with_comments.f +8 -0
  483. numpy/f2py/tests/src/crackfortran/foo_deps.f90 +6 -0
  484. numpy/f2py/tests/src/crackfortran/gh15035.f +16 -0
  485. numpy/f2py/tests/src/crackfortran/gh17859.f +12 -0
  486. numpy/f2py/tests/src/crackfortran/gh22648.pyf +7 -0
  487. numpy/f2py/tests/src/crackfortran/gh23533.f +5 -0
  488. numpy/f2py/tests/src/crackfortran/gh23598.f90 +4 -0
  489. numpy/f2py/tests/src/crackfortran/gh23598Warn.f90 +11 -0
  490. numpy/f2py/tests/src/crackfortran/gh23879.f90 +20 -0
  491. numpy/f2py/tests/src/crackfortran/gh27697.f90 +12 -0
  492. numpy/f2py/tests/src/crackfortran/gh2848.f90 +13 -0
  493. numpy/f2py/tests/src/crackfortran/operators.f90 +49 -0
  494. numpy/f2py/tests/src/crackfortran/privatemod.f90 +11 -0
  495. numpy/f2py/tests/src/crackfortran/publicmod.f90 +10 -0
  496. numpy/f2py/tests/src/crackfortran/pubprivmod.f90 +10 -0
  497. numpy/f2py/tests/src/crackfortran/unicode_comment.f90 +4 -0
  498. numpy/f2py/tests/src/f2cmap/.f2py_f2cmap +1 -0
  499. numpy/f2py/tests/src/f2cmap/isoFortranEnvMap.f90 +9 -0
  500. numpy/f2py/tests/src/isocintrin/isoCtests.f90 +34 -0
  501. numpy/f2py/tests/src/kind/foo.f90 +20 -0
  502. numpy/f2py/tests/src/mixed/foo.f +5 -0
  503. numpy/f2py/tests/src/mixed/foo_fixed.f90 +8 -0
  504. numpy/f2py/tests/src/mixed/foo_free.f90 +8 -0
  505. numpy/f2py/tests/src/modules/gh25337/data.f90 +8 -0
  506. numpy/f2py/tests/src/modules/gh25337/use_data.f90 +6 -0
  507. numpy/f2py/tests/src/modules/gh26920/two_mods_with_no_public_entities.f90 +21 -0
  508. numpy/f2py/tests/src/modules/gh26920/two_mods_with_one_public_routine.f90 +21 -0
  509. numpy/f2py/tests/src/modules/module_data_docstring.f90 +12 -0
  510. numpy/f2py/tests/src/modules/use_modules.f90 +20 -0
  511. numpy/f2py/tests/src/negative_bounds/issue_20853.f90 +7 -0
  512. numpy/f2py/tests/src/parameter/constant_array.f90 +45 -0
  513. numpy/f2py/tests/src/parameter/constant_both.f90 +57 -0
  514. numpy/f2py/tests/src/parameter/constant_compound.f90 +15 -0
  515. numpy/f2py/tests/src/parameter/constant_integer.f90 +22 -0
  516. numpy/f2py/tests/src/parameter/constant_non_compound.f90 +23 -0
  517. numpy/f2py/tests/src/parameter/constant_real.f90 +23 -0
  518. numpy/f2py/tests/src/quoted_character/foo.f +14 -0
  519. numpy/f2py/tests/src/regression/AB.inc +1 -0
  520. numpy/f2py/tests/src/regression/assignOnlyModule.f90 +25 -0
  521. numpy/f2py/tests/src/regression/datonly.f90 +17 -0
  522. numpy/f2py/tests/src/regression/f77comments.f +26 -0
  523. numpy/f2py/tests/src/regression/f77fixedform.f95 +5 -0
  524. numpy/f2py/tests/src/regression/f90continuation.f90 +9 -0
  525. numpy/f2py/tests/src/regression/incfile.f90 +5 -0
  526. numpy/f2py/tests/src/regression/inout.f90 +9 -0
  527. numpy/f2py/tests/src/regression/lower_f2py_fortran.f90 +5 -0
  528. numpy/f2py/tests/src/regression/mod_derived_types.f90 +23 -0
  529. numpy/f2py/tests/src/return_character/foo77.f +45 -0
  530. numpy/f2py/tests/src/return_character/foo90.f90 +48 -0
  531. numpy/f2py/tests/src/return_complex/foo77.f +45 -0
  532. numpy/f2py/tests/src/return_complex/foo90.f90 +48 -0
  533. numpy/f2py/tests/src/return_integer/foo77.f +56 -0
  534. numpy/f2py/tests/src/return_integer/foo90.f90 +59 -0
  535. numpy/f2py/tests/src/return_logical/foo77.f +56 -0
  536. numpy/f2py/tests/src/return_logical/foo90.f90 +59 -0
  537. numpy/f2py/tests/src/return_real/foo77.f +45 -0
  538. numpy/f2py/tests/src/return_real/foo90.f90 +48 -0
  539. numpy/f2py/tests/src/routines/funcfortranname.f +5 -0
  540. numpy/f2py/tests/src/routines/funcfortranname.pyf +11 -0
  541. numpy/f2py/tests/src/routines/subrout.f +4 -0
  542. numpy/f2py/tests/src/routines/subrout.pyf +10 -0
  543. numpy/f2py/tests/src/size/foo.f90 +44 -0
  544. numpy/f2py/tests/src/string/char.f90 +29 -0
  545. numpy/f2py/tests/src/string/fixed_string.f90 +34 -0
  546. numpy/f2py/tests/src/string/gh24008.f +8 -0
  547. numpy/f2py/tests/src/string/gh24662.f90 +7 -0
  548. numpy/f2py/tests/src/string/gh25286.f90 +14 -0
  549. numpy/f2py/tests/src/string/gh25286.pyf +12 -0
  550. numpy/f2py/tests/src/string/gh25286_bc.pyf +12 -0
  551. numpy/f2py/tests/src/string/scalar_string.f90 +9 -0
  552. numpy/f2py/tests/src/string/string.f +12 -0
  553. numpy/f2py/tests/src/value_attrspec/gh21665.f90 +9 -0
  554. numpy/f2py/tests/test_abstract_interface.py +26 -0
  555. numpy/f2py/tests/test_array_from_pyobj.py +678 -0
  556. numpy/f2py/tests/test_assumed_shape.py +50 -0
  557. numpy/f2py/tests/test_block_docstring.py +20 -0
  558. numpy/f2py/tests/test_callback.py +263 -0
  559. numpy/f2py/tests/test_character.py +641 -0
  560. numpy/f2py/tests/test_common.py +23 -0
  561. numpy/f2py/tests/test_crackfortran.py +421 -0
  562. numpy/f2py/tests/test_data.py +71 -0
  563. numpy/f2py/tests/test_docs.py +66 -0
  564. numpy/f2py/tests/test_f2cmap.py +17 -0
  565. numpy/f2py/tests/test_f2py2e.py +983 -0
  566. numpy/f2py/tests/test_isoc.py +56 -0
  567. numpy/f2py/tests/test_kind.py +52 -0
  568. numpy/f2py/tests/test_mixed.py +35 -0
  569. numpy/f2py/tests/test_modules.py +83 -0
  570. numpy/f2py/tests/test_parameter.py +129 -0
  571. numpy/f2py/tests/test_pyf_src.py +43 -0
  572. numpy/f2py/tests/test_quoted_character.py +18 -0
  573. numpy/f2py/tests/test_regression.py +187 -0
  574. numpy/f2py/tests/test_return_character.py +48 -0
  575. numpy/f2py/tests/test_return_complex.py +67 -0
  576. numpy/f2py/tests/test_return_integer.py +55 -0
  577. numpy/f2py/tests/test_return_logical.py +65 -0
  578. numpy/f2py/tests/test_return_real.py +109 -0
  579. numpy/f2py/tests/test_routines.py +29 -0
  580. numpy/f2py/tests/test_semicolon_split.py +75 -0
  581. numpy/f2py/tests/test_size.py +45 -0
  582. numpy/f2py/tests/test_string.py +100 -0
  583. numpy/f2py/tests/test_symbolic.py +500 -0
  584. numpy/f2py/tests/test_value_attrspec.py +15 -0
  585. numpy/f2py/tests/util.py +442 -0
  586. numpy/f2py/use_rules.py +99 -0
  587. numpy/f2py/use_rules.pyi +9 -0
  588. numpy/fft/__init__.py +213 -0
  589. numpy/fft/__init__.pyi +38 -0
  590. numpy/fft/_helper.py +235 -0
  591. numpy/fft/_helper.pyi +44 -0
  592. numpy/fft/_pocketfft.py +1693 -0
  593. numpy/fft/_pocketfft.pyi +137 -0
  594. numpy/fft/_pocketfft_umath.pypy311-pp73-darwin.so +0 -0
  595. numpy/fft/tests/__init__.py +0 -0
  596. numpy/fft/tests/test_helper.py +167 -0
  597. numpy/fft/tests/test_pocketfft.py +589 -0
  598. numpy/lib/__init__.py +97 -0
  599. numpy/lib/__init__.pyi +52 -0
  600. numpy/lib/_array_utils_impl.py +62 -0
  601. numpy/lib/_array_utils_impl.pyi +10 -0
  602. numpy/lib/_arraypad_impl.py +926 -0
  603. numpy/lib/_arraypad_impl.pyi +88 -0
  604. numpy/lib/_arraysetops_impl.py +1158 -0
  605. numpy/lib/_arraysetops_impl.pyi +462 -0
  606. numpy/lib/_arrayterator_impl.py +224 -0
  607. numpy/lib/_arrayterator_impl.pyi +45 -0
  608. numpy/lib/_datasource.py +700 -0
  609. numpy/lib/_datasource.pyi +30 -0
  610. numpy/lib/_format_impl.py +1036 -0
  611. numpy/lib/_format_impl.pyi +56 -0
  612. numpy/lib/_function_base_impl.py +5760 -0
  613. numpy/lib/_function_base_impl.pyi +2324 -0
  614. numpy/lib/_histograms_impl.py +1085 -0
  615. numpy/lib/_histograms_impl.pyi +40 -0
  616. numpy/lib/_index_tricks_impl.py +1048 -0
  617. numpy/lib/_index_tricks_impl.pyi +267 -0
  618. numpy/lib/_iotools.py +900 -0
  619. numpy/lib/_iotools.pyi +116 -0
  620. numpy/lib/_nanfunctions_impl.py +2006 -0
  621. numpy/lib/_nanfunctions_impl.pyi +48 -0
  622. numpy/lib/_npyio_impl.py +2583 -0
  623. numpy/lib/_npyio_impl.pyi +299 -0
  624. numpy/lib/_polynomial_impl.py +1465 -0
  625. numpy/lib/_polynomial_impl.pyi +338 -0
  626. numpy/lib/_scimath_impl.py +642 -0
  627. numpy/lib/_scimath_impl.pyi +93 -0
  628. numpy/lib/_shape_base_impl.py +1289 -0
  629. numpy/lib/_shape_base_impl.pyi +236 -0
  630. numpy/lib/_stride_tricks_impl.py +582 -0
  631. numpy/lib/_stride_tricks_impl.pyi +73 -0
  632. numpy/lib/_twodim_base_impl.py +1201 -0
  633. numpy/lib/_twodim_base_impl.pyi +408 -0
  634. numpy/lib/_type_check_impl.py +710 -0
  635. numpy/lib/_type_check_impl.pyi +348 -0
  636. numpy/lib/_ufunclike_impl.py +199 -0
  637. numpy/lib/_ufunclike_impl.pyi +60 -0
  638. numpy/lib/_user_array_impl.py +310 -0
  639. numpy/lib/_user_array_impl.pyi +226 -0
  640. numpy/lib/_utils_impl.py +784 -0
  641. numpy/lib/_utils_impl.pyi +22 -0
  642. numpy/lib/_version.py +153 -0
  643. numpy/lib/_version.pyi +17 -0
  644. numpy/lib/array_utils.py +7 -0
  645. numpy/lib/array_utils.pyi +6 -0
  646. numpy/lib/format.py +24 -0
  647. numpy/lib/format.pyi +24 -0
  648. numpy/lib/introspect.py +94 -0
  649. numpy/lib/introspect.pyi +3 -0
  650. numpy/lib/mixins.py +180 -0
  651. numpy/lib/mixins.pyi +78 -0
  652. numpy/lib/npyio.py +1 -0
  653. numpy/lib/npyio.pyi +5 -0
  654. numpy/lib/recfunctions.py +1681 -0
  655. numpy/lib/recfunctions.pyi +444 -0
  656. numpy/lib/scimath.py +13 -0
  657. numpy/lib/scimath.pyi +12 -0
  658. numpy/lib/stride_tricks.py +1 -0
  659. numpy/lib/stride_tricks.pyi +4 -0
  660. numpy/lib/tests/__init__.py +0 -0
  661. numpy/lib/tests/data/py2-np0-objarr.npy +0 -0
  662. numpy/lib/tests/data/py2-objarr.npy +0 -0
  663. numpy/lib/tests/data/py2-objarr.npz +0 -0
  664. numpy/lib/tests/data/py3-objarr.npy +0 -0
  665. numpy/lib/tests/data/py3-objarr.npz +0 -0
  666. numpy/lib/tests/data/python3.npy +0 -0
  667. numpy/lib/tests/data/win64python2.npy +0 -0
  668. numpy/lib/tests/test__datasource.py +328 -0
  669. numpy/lib/tests/test__iotools.py +358 -0
  670. numpy/lib/tests/test__version.py +64 -0
  671. numpy/lib/tests/test_array_utils.py +32 -0
  672. numpy/lib/tests/test_arraypad.py +1427 -0
  673. numpy/lib/tests/test_arraysetops.py +1302 -0
  674. numpy/lib/tests/test_arrayterator.py +45 -0
  675. numpy/lib/tests/test_format.py +1054 -0
  676. numpy/lib/tests/test_function_base.py +4750 -0
  677. numpy/lib/tests/test_histograms.py +855 -0
  678. numpy/lib/tests/test_index_tricks.py +693 -0
  679. numpy/lib/tests/test_io.py +2857 -0
  680. numpy/lib/tests/test_loadtxt.py +1099 -0
  681. numpy/lib/tests/test_mixins.py +215 -0
  682. numpy/lib/tests/test_nanfunctions.py +1438 -0
  683. numpy/lib/tests/test_packbits.py +376 -0
  684. numpy/lib/tests/test_polynomial.py +325 -0
  685. numpy/lib/tests/test_recfunctions.py +1042 -0
  686. numpy/lib/tests/test_regression.py +231 -0
  687. numpy/lib/tests/test_shape_base.py +813 -0
  688. numpy/lib/tests/test_stride_tricks.py +655 -0
  689. numpy/lib/tests/test_twodim_base.py +559 -0
  690. numpy/lib/tests/test_type_check.py +473 -0
  691. numpy/lib/tests/test_ufunclike.py +97 -0
  692. numpy/lib/tests/test_utils.py +80 -0
  693. numpy/lib/user_array.py +1 -0
  694. numpy/lib/user_array.pyi +1 -0
  695. numpy/linalg/__init__.py +95 -0
  696. numpy/linalg/__init__.pyi +71 -0
  697. numpy/linalg/_linalg.py +3657 -0
  698. numpy/linalg/_linalg.pyi +548 -0
  699. numpy/linalg/_umath_linalg.pyi +60 -0
  700. numpy/linalg/_umath_linalg.pypy311-pp73-darwin.so +0 -0
  701. numpy/linalg/lapack_lite.pyi +143 -0
  702. numpy/linalg/lapack_lite.pypy311-pp73-darwin.so +0 -0
  703. numpy/linalg/tests/__init__.py +0 -0
  704. numpy/linalg/tests/test_deprecations.py +21 -0
  705. numpy/linalg/tests/test_linalg.py +2442 -0
  706. numpy/linalg/tests/test_regression.py +182 -0
  707. numpy/ma/API_CHANGES.txt +135 -0
  708. numpy/ma/LICENSE +24 -0
  709. numpy/ma/README.rst +236 -0
  710. numpy/ma/__init__.py +53 -0
  711. numpy/ma/__init__.pyi +458 -0
  712. numpy/ma/core.py +8929 -0
  713. numpy/ma/core.pyi +3720 -0
  714. numpy/ma/extras.py +2266 -0
  715. numpy/ma/extras.pyi +297 -0
  716. numpy/ma/mrecords.py +762 -0
  717. numpy/ma/mrecords.pyi +96 -0
  718. numpy/ma/tests/__init__.py +0 -0
  719. numpy/ma/tests/test_arrayobject.py +40 -0
  720. numpy/ma/tests/test_core.py +6008 -0
  721. numpy/ma/tests/test_deprecations.py +65 -0
  722. numpy/ma/tests/test_extras.py +1945 -0
  723. numpy/ma/tests/test_mrecords.py +495 -0
  724. numpy/ma/tests/test_old_ma.py +939 -0
  725. numpy/ma/tests/test_regression.py +83 -0
  726. numpy/ma/tests/test_subclassing.py +469 -0
  727. numpy/ma/testutils.py +294 -0
  728. numpy/ma/testutils.pyi +69 -0
  729. numpy/matlib.py +380 -0
  730. numpy/matlib.pyi +580 -0
  731. numpy/matrixlib/__init__.py +12 -0
  732. numpy/matrixlib/__init__.pyi +3 -0
  733. numpy/matrixlib/defmatrix.py +1119 -0
  734. numpy/matrixlib/defmatrix.pyi +218 -0
  735. numpy/matrixlib/tests/__init__.py +0 -0
  736. numpy/matrixlib/tests/test_defmatrix.py +455 -0
  737. numpy/matrixlib/tests/test_interaction.py +360 -0
  738. numpy/matrixlib/tests/test_masked_matrix.py +240 -0
  739. numpy/matrixlib/tests/test_matrix_linalg.py +110 -0
  740. numpy/matrixlib/tests/test_multiarray.py +17 -0
  741. numpy/matrixlib/tests/test_numeric.py +18 -0
  742. numpy/matrixlib/tests/test_regression.py +31 -0
  743. numpy/polynomial/__init__.py +187 -0
  744. numpy/polynomial/__init__.pyi +31 -0
  745. numpy/polynomial/_polybase.py +1191 -0
  746. numpy/polynomial/_polybase.pyi +262 -0
  747. numpy/polynomial/_polytypes.pyi +501 -0
  748. numpy/polynomial/chebyshev.py +2001 -0
  749. numpy/polynomial/chebyshev.pyi +180 -0
  750. numpy/polynomial/hermite.py +1738 -0
  751. numpy/polynomial/hermite.pyi +106 -0
  752. numpy/polynomial/hermite_e.py +1640 -0
  753. numpy/polynomial/hermite_e.pyi +106 -0
  754. numpy/polynomial/laguerre.py +1673 -0
  755. numpy/polynomial/laguerre.pyi +100 -0
  756. numpy/polynomial/legendre.py +1603 -0
  757. numpy/polynomial/legendre.pyi +100 -0
  758. numpy/polynomial/polynomial.py +1625 -0
  759. numpy/polynomial/polynomial.pyi +109 -0
  760. numpy/polynomial/polyutils.py +759 -0
  761. numpy/polynomial/polyutils.pyi +307 -0
  762. numpy/polynomial/tests/__init__.py +0 -0
  763. numpy/polynomial/tests/test_chebyshev.py +618 -0
  764. numpy/polynomial/tests/test_classes.py +613 -0
  765. numpy/polynomial/tests/test_hermite.py +553 -0
  766. numpy/polynomial/tests/test_hermite_e.py +554 -0
  767. numpy/polynomial/tests/test_laguerre.py +535 -0
  768. numpy/polynomial/tests/test_legendre.py +566 -0
  769. numpy/polynomial/tests/test_polynomial.py +691 -0
  770. numpy/polynomial/tests/test_polyutils.py +123 -0
  771. numpy/polynomial/tests/test_printing.py +557 -0
  772. numpy/polynomial/tests/test_symbol.py +217 -0
  773. numpy/py.typed +0 -0
  774. numpy/random/LICENSE.md +71 -0
  775. numpy/random/__init__.pxd +14 -0
  776. numpy/random/__init__.py +213 -0
  777. numpy/random/__init__.pyi +124 -0
  778. numpy/random/_bounded_integers.pxd +29 -0
  779. numpy/random/_bounded_integers.pyi +1 -0
  780. numpy/random/_bounded_integers.pypy311-pp73-darwin.so +0 -0
  781. numpy/random/_common.pxd +110 -0
  782. numpy/random/_common.pyi +16 -0
  783. numpy/random/_common.pypy311-pp73-darwin.so +0 -0
  784. numpy/random/_examples/cffi/extending.py +44 -0
  785. numpy/random/_examples/cffi/parse.py +53 -0
  786. numpy/random/_examples/cython/extending.pyx +77 -0
  787. numpy/random/_examples/cython/extending_distributions.pyx +117 -0
  788. numpy/random/_examples/cython/meson.build +53 -0
  789. numpy/random/_examples/numba/extending.py +86 -0
  790. numpy/random/_examples/numba/extending_distributions.py +67 -0
  791. numpy/random/_generator.pyi +862 -0
  792. numpy/random/_generator.pypy311-pp73-darwin.so +0 -0
  793. numpy/random/_mt19937.pyi +27 -0
  794. numpy/random/_mt19937.pypy311-pp73-darwin.so +0 -0
  795. numpy/random/_pcg64.pyi +41 -0
  796. numpy/random/_pcg64.pypy311-pp73-darwin.so +0 -0
  797. numpy/random/_philox.pyi +36 -0
  798. numpy/random/_philox.pypy311-pp73-darwin.so +0 -0
  799. numpy/random/_pickle.py +88 -0
  800. numpy/random/_pickle.pyi +43 -0
  801. numpy/random/_sfc64.pyi +25 -0
  802. numpy/random/_sfc64.pypy311-pp73-darwin.so +0 -0
  803. numpy/random/bit_generator.pxd +40 -0
  804. numpy/random/bit_generator.pyi +123 -0
  805. numpy/random/bit_generator.pypy311-pp73-darwin.so +0 -0
  806. numpy/random/c_distributions.pxd +119 -0
  807. numpy/random/lib/libnpyrandom.a +0 -0
  808. numpy/random/mtrand.pyi +759 -0
  809. numpy/random/mtrand.pypy311-pp73-darwin.so +0 -0
  810. numpy/random/tests/__init__.py +0 -0
  811. numpy/random/tests/data/__init__.py +0 -0
  812. numpy/random/tests/data/generator_pcg64_np121.pkl.gz +0 -0
  813. numpy/random/tests/data/generator_pcg64_np126.pkl.gz +0 -0
  814. numpy/random/tests/data/mt19937-testset-1.csv +1001 -0
  815. numpy/random/tests/data/mt19937-testset-2.csv +1001 -0
  816. numpy/random/tests/data/pcg64-testset-1.csv +1001 -0
  817. numpy/random/tests/data/pcg64-testset-2.csv +1001 -0
  818. numpy/random/tests/data/pcg64dxsm-testset-1.csv +1001 -0
  819. numpy/random/tests/data/pcg64dxsm-testset-2.csv +1001 -0
  820. numpy/random/tests/data/philox-testset-1.csv +1001 -0
  821. numpy/random/tests/data/philox-testset-2.csv +1001 -0
  822. numpy/random/tests/data/sfc64-testset-1.csv +1001 -0
  823. numpy/random/tests/data/sfc64-testset-2.csv +1001 -0
  824. numpy/random/tests/data/sfc64_np126.pkl.gz +0 -0
  825. numpy/random/tests/test_direct.py +595 -0
  826. numpy/random/tests/test_extending.py +131 -0
  827. numpy/random/tests/test_generator_mt19937.py +2825 -0
  828. numpy/random/tests/test_generator_mt19937_regressions.py +221 -0
  829. numpy/random/tests/test_random.py +1724 -0
  830. numpy/random/tests/test_randomstate.py +2099 -0
  831. numpy/random/tests/test_randomstate_regression.py +213 -0
  832. numpy/random/tests/test_regression.py +175 -0
  833. numpy/random/tests/test_seed_sequence.py +79 -0
  834. numpy/random/tests/test_smoke.py +882 -0
  835. numpy/rec/__init__.py +2 -0
  836. numpy/rec/__init__.pyi +23 -0
  837. numpy/strings/__init__.py +2 -0
  838. numpy/strings/__init__.pyi +97 -0
  839. numpy/testing/__init__.py +22 -0
  840. numpy/testing/__init__.pyi +107 -0
  841. numpy/testing/_private/__init__.py +0 -0
  842. numpy/testing/_private/__init__.pyi +0 -0
  843. numpy/testing/_private/extbuild.py +250 -0
  844. numpy/testing/_private/extbuild.pyi +25 -0
  845. numpy/testing/_private/utils.py +2830 -0
  846. numpy/testing/_private/utils.pyi +505 -0
  847. numpy/testing/overrides.py +84 -0
  848. numpy/testing/overrides.pyi +10 -0
  849. numpy/testing/print_coercion_tables.py +207 -0
  850. numpy/testing/print_coercion_tables.pyi +26 -0
  851. numpy/testing/tests/__init__.py +0 -0
  852. numpy/testing/tests/test_utils.py +2123 -0
  853. numpy/tests/__init__.py +0 -0
  854. numpy/tests/test__all__.py +10 -0
  855. numpy/tests/test_configtool.py +51 -0
  856. numpy/tests/test_ctypeslib.py +383 -0
  857. numpy/tests/test_lazyloading.py +42 -0
  858. numpy/tests/test_matlib.py +59 -0
  859. numpy/tests/test_numpy_config.py +47 -0
  860. numpy/tests/test_numpy_version.py +54 -0
  861. numpy/tests/test_public_api.py +807 -0
  862. numpy/tests/test_reloading.py +76 -0
  863. numpy/tests/test_scripts.py +48 -0
  864. numpy/tests/test_warnings.py +79 -0
  865. numpy/typing/__init__.py +233 -0
  866. numpy/typing/__init__.pyi +3 -0
  867. numpy/typing/mypy_plugin.py +200 -0
  868. numpy/typing/tests/__init__.py +0 -0
  869. numpy/typing/tests/data/fail/arithmetic.pyi +126 -0
  870. numpy/typing/tests/data/fail/array_constructors.pyi +34 -0
  871. numpy/typing/tests/data/fail/array_like.pyi +15 -0
  872. numpy/typing/tests/data/fail/array_pad.pyi +6 -0
  873. numpy/typing/tests/data/fail/arrayprint.pyi +15 -0
  874. numpy/typing/tests/data/fail/arrayterator.pyi +14 -0
  875. numpy/typing/tests/data/fail/bitwise_ops.pyi +17 -0
  876. numpy/typing/tests/data/fail/char.pyi +63 -0
  877. numpy/typing/tests/data/fail/chararray.pyi +61 -0
  878. numpy/typing/tests/data/fail/comparisons.pyi +27 -0
  879. numpy/typing/tests/data/fail/constants.pyi +3 -0
  880. numpy/typing/tests/data/fail/datasource.pyi +16 -0
  881. numpy/typing/tests/data/fail/dtype.pyi +17 -0
  882. numpy/typing/tests/data/fail/einsumfunc.pyi +12 -0
  883. numpy/typing/tests/data/fail/flatiter.pyi +38 -0
  884. numpy/typing/tests/data/fail/fromnumeric.pyi +148 -0
  885. numpy/typing/tests/data/fail/histograms.pyi +12 -0
  886. numpy/typing/tests/data/fail/index_tricks.pyi +14 -0
  887. numpy/typing/tests/data/fail/lib_function_base.pyi +60 -0
  888. numpy/typing/tests/data/fail/lib_polynomial.pyi +29 -0
  889. numpy/typing/tests/data/fail/lib_utils.pyi +3 -0
  890. numpy/typing/tests/data/fail/lib_version.pyi +6 -0
  891. numpy/typing/tests/data/fail/linalg.pyi +52 -0
  892. numpy/typing/tests/data/fail/ma.pyi +155 -0
  893. numpy/typing/tests/data/fail/memmap.pyi +5 -0
  894. numpy/typing/tests/data/fail/modules.pyi +17 -0
  895. numpy/typing/tests/data/fail/multiarray.pyi +52 -0
  896. numpy/typing/tests/data/fail/ndarray.pyi +11 -0
  897. numpy/typing/tests/data/fail/ndarray_misc.pyi +49 -0
  898. numpy/typing/tests/data/fail/nditer.pyi +8 -0
  899. numpy/typing/tests/data/fail/nested_sequence.pyi +17 -0
  900. numpy/typing/tests/data/fail/npyio.pyi +24 -0
  901. numpy/typing/tests/data/fail/numerictypes.pyi +5 -0
  902. numpy/typing/tests/data/fail/random.pyi +62 -0
  903. numpy/typing/tests/data/fail/rec.pyi +17 -0
  904. numpy/typing/tests/data/fail/scalars.pyi +86 -0
  905. numpy/typing/tests/data/fail/shape.pyi +7 -0
  906. numpy/typing/tests/data/fail/shape_base.pyi +8 -0
  907. numpy/typing/tests/data/fail/stride_tricks.pyi +9 -0
  908. numpy/typing/tests/data/fail/strings.pyi +52 -0
  909. numpy/typing/tests/data/fail/testing.pyi +28 -0
  910. numpy/typing/tests/data/fail/twodim_base.pyi +39 -0
  911. numpy/typing/tests/data/fail/type_check.pyi +12 -0
  912. numpy/typing/tests/data/fail/ufunc_config.pyi +21 -0
  913. numpy/typing/tests/data/fail/ufunclike.pyi +21 -0
  914. numpy/typing/tests/data/fail/ufuncs.pyi +17 -0
  915. numpy/typing/tests/data/fail/warnings_and_errors.pyi +5 -0
  916. numpy/typing/tests/data/misc/extended_precision.pyi +9 -0
  917. numpy/typing/tests/data/mypy.ini +8 -0
  918. numpy/typing/tests/data/pass/arithmetic.py +614 -0
  919. numpy/typing/tests/data/pass/array_constructors.py +138 -0
  920. numpy/typing/tests/data/pass/array_like.py +43 -0
  921. numpy/typing/tests/data/pass/arrayprint.py +37 -0
  922. numpy/typing/tests/data/pass/arrayterator.py +28 -0
  923. numpy/typing/tests/data/pass/bitwise_ops.py +131 -0
  924. numpy/typing/tests/data/pass/comparisons.py +316 -0
  925. numpy/typing/tests/data/pass/dtype.py +57 -0
  926. numpy/typing/tests/data/pass/einsumfunc.py +36 -0
  927. numpy/typing/tests/data/pass/flatiter.py +26 -0
  928. numpy/typing/tests/data/pass/fromnumeric.py +272 -0
  929. numpy/typing/tests/data/pass/index_tricks.py +62 -0
  930. numpy/typing/tests/data/pass/lib_user_array.py +22 -0
  931. numpy/typing/tests/data/pass/lib_utils.py +19 -0
  932. numpy/typing/tests/data/pass/lib_version.py +18 -0
  933. numpy/typing/tests/data/pass/literal.py +52 -0
  934. numpy/typing/tests/data/pass/ma.py +199 -0
  935. numpy/typing/tests/data/pass/mod.py +149 -0
  936. numpy/typing/tests/data/pass/modules.py +45 -0
  937. numpy/typing/tests/data/pass/multiarray.py +77 -0
  938. numpy/typing/tests/data/pass/ndarray_conversion.py +81 -0
  939. numpy/typing/tests/data/pass/ndarray_misc.py +199 -0
  940. numpy/typing/tests/data/pass/ndarray_shape_manipulation.py +47 -0
  941. numpy/typing/tests/data/pass/nditer.py +4 -0
  942. numpy/typing/tests/data/pass/numeric.py +90 -0
  943. numpy/typing/tests/data/pass/numerictypes.py +17 -0
  944. numpy/typing/tests/data/pass/random.py +1498 -0
  945. numpy/typing/tests/data/pass/recfunctions.py +164 -0
  946. numpy/typing/tests/data/pass/scalars.py +249 -0
  947. numpy/typing/tests/data/pass/shape.py +19 -0
  948. numpy/typing/tests/data/pass/simple.py +170 -0
  949. numpy/typing/tests/data/pass/ufunc_config.py +64 -0
  950. numpy/typing/tests/data/pass/ufunclike.py +52 -0
  951. numpy/typing/tests/data/pass/ufuncs.py +16 -0
  952. numpy/typing/tests/data/pass/warnings_and_errors.py +6 -0
  953. numpy/typing/tests/data/reveal/arithmetic.pyi +719 -0
  954. numpy/typing/tests/data/reveal/array_api_info.pyi +70 -0
  955. numpy/typing/tests/data/reveal/array_constructors.pyi +277 -0
  956. numpy/typing/tests/data/reveal/arraypad.pyi +27 -0
  957. numpy/typing/tests/data/reveal/arrayprint.pyi +25 -0
  958. numpy/typing/tests/data/reveal/arraysetops.pyi +74 -0
  959. numpy/typing/tests/data/reveal/arrayterator.pyi +27 -0
  960. numpy/typing/tests/data/reveal/bitwise_ops.pyi +166 -0
  961. numpy/typing/tests/data/reveal/char.pyi +225 -0
  962. numpy/typing/tests/data/reveal/chararray.pyi +138 -0
  963. numpy/typing/tests/data/reveal/comparisons.pyi +264 -0
  964. numpy/typing/tests/data/reveal/constants.pyi +14 -0
  965. numpy/typing/tests/data/reveal/ctypeslib.pyi +81 -0
  966. numpy/typing/tests/data/reveal/datasource.pyi +23 -0
  967. numpy/typing/tests/data/reveal/dtype.pyi +132 -0
  968. numpy/typing/tests/data/reveal/einsumfunc.pyi +39 -0
  969. numpy/typing/tests/data/reveal/emath.pyi +54 -0
  970. numpy/typing/tests/data/reveal/fft.pyi +37 -0
  971. numpy/typing/tests/data/reveal/flatiter.pyi +86 -0
  972. numpy/typing/tests/data/reveal/fromnumeric.pyi +347 -0
  973. numpy/typing/tests/data/reveal/getlimits.pyi +53 -0
  974. numpy/typing/tests/data/reveal/histograms.pyi +25 -0
  975. numpy/typing/tests/data/reveal/index_tricks.pyi +70 -0
  976. numpy/typing/tests/data/reveal/lib_function_base.pyi +409 -0
  977. numpy/typing/tests/data/reveal/lib_polynomial.pyi +147 -0
  978. numpy/typing/tests/data/reveal/lib_utils.pyi +17 -0
  979. numpy/typing/tests/data/reveal/lib_version.pyi +20 -0
  980. numpy/typing/tests/data/reveal/linalg.pyi +154 -0
  981. numpy/typing/tests/data/reveal/ma.pyi +1098 -0
  982. numpy/typing/tests/data/reveal/matrix.pyi +73 -0
  983. numpy/typing/tests/data/reveal/memmap.pyi +19 -0
  984. numpy/typing/tests/data/reveal/mod.pyi +178 -0
  985. numpy/typing/tests/data/reveal/modules.pyi +51 -0
  986. numpy/typing/tests/data/reveal/multiarray.pyi +197 -0
  987. numpy/typing/tests/data/reveal/nbit_base_example.pyi +20 -0
  988. numpy/typing/tests/data/reveal/ndarray_assignability.pyi +82 -0
  989. numpy/typing/tests/data/reveal/ndarray_conversion.pyi +83 -0
  990. numpy/typing/tests/data/reveal/ndarray_misc.pyi +246 -0
  991. numpy/typing/tests/data/reveal/ndarray_shape_manipulation.pyi +47 -0
  992. numpy/typing/tests/data/reveal/nditer.pyi +49 -0
  993. numpy/typing/tests/data/reveal/nested_sequence.pyi +25 -0
  994. numpy/typing/tests/data/reveal/npyio.pyi +83 -0
  995. numpy/typing/tests/data/reveal/numeric.pyi +170 -0
  996. numpy/typing/tests/data/reveal/numerictypes.pyi +16 -0
  997. numpy/typing/tests/data/reveal/polynomial_polybase.pyi +217 -0
  998. numpy/typing/tests/data/reveal/polynomial_polyutils.pyi +218 -0
  999. numpy/typing/tests/data/reveal/polynomial_series.pyi +138 -0
  1000. numpy/typing/tests/data/reveal/random.pyi +1546 -0
  1001. numpy/typing/tests/data/reveal/rec.pyi +171 -0
  1002. numpy/typing/tests/data/reveal/scalars.pyi +191 -0
  1003. numpy/typing/tests/data/reveal/shape.pyi +13 -0
  1004. numpy/typing/tests/data/reveal/shape_base.pyi +52 -0
  1005. numpy/typing/tests/data/reveal/stride_tricks.pyi +27 -0
  1006. numpy/typing/tests/data/reveal/strings.pyi +196 -0
  1007. numpy/typing/tests/data/reveal/testing.pyi +198 -0
  1008. numpy/typing/tests/data/reveal/twodim_base.pyi +225 -0
  1009. numpy/typing/tests/data/reveal/type_check.pyi +67 -0
  1010. numpy/typing/tests/data/reveal/ufunc_config.pyi +29 -0
  1011. numpy/typing/tests/data/reveal/ufunclike.pyi +31 -0
  1012. numpy/typing/tests/data/reveal/ufuncs.pyi +142 -0
  1013. numpy/typing/tests/data/reveal/warnings_and_errors.pyi +11 -0
  1014. numpy/typing/tests/test_isfile.py +38 -0
  1015. numpy/typing/tests/test_runtime.py +110 -0
  1016. numpy/typing/tests/test_typing.py +205 -0
  1017. numpy/version.py +11 -0
  1018. numpy/version.pyi +9 -0
  1019. numpy-2.4.1.dist-info/METADATA +139 -0
  1020. numpy-2.4.1.dist-info/RECORD +1039 -0
  1021. numpy-2.4.1.dist-info/WHEEL +6 -0
  1022. numpy-2.4.1.dist-info/entry_points.txt +13 -0
  1023. numpy-2.4.1.dist-info/licenses/LICENSE.txt +935 -0
  1024. numpy-2.4.1.dist-info/licenses/numpy/_core/include/numpy/libdivide/LICENSE.txt +21 -0
  1025. numpy-2.4.1.dist-info/licenses/numpy/_core/src/common/pythoncapi-compat/COPYING +14 -0
  1026. numpy-2.4.1.dist-info/licenses/numpy/_core/src/highway/LICENSE +371 -0
  1027. numpy-2.4.1.dist-info/licenses/numpy/_core/src/multiarray/dragon4_LICENSE.txt +27 -0
  1028. numpy-2.4.1.dist-info/licenses/numpy/_core/src/npysort/x86-simd-sort/LICENSE.md +28 -0
  1029. numpy-2.4.1.dist-info/licenses/numpy/_core/src/umath/svml/LICENSE +30 -0
  1030. numpy-2.4.1.dist-info/licenses/numpy/fft/pocketfft/LICENSE.md +25 -0
  1031. numpy-2.4.1.dist-info/licenses/numpy/linalg/lapack_lite/LICENSE.txt +48 -0
  1032. numpy-2.4.1.dist-info/licenses/numpy/ma/LICENSE +24 -0
  1033. numpy-2.4.1.dist-info/licenses/numpy/random/LICENSE.md +71 -0
  1034. numpy-2.4.1.dist-info/licenses/numpy/random/src/distributions/LICENSE.md +61 -0
  1035. numpy-2.4.1.dist-info/licenses/numpy/random/src/mt19937/LICENSE.md +61 -0
  1036. numpy-2.4.1.dist-info/licenses/numpy/random/src/pcg64/LICENSE.md +22 -0
  1037. numpy-2.4.1.dist-info/licenses/numpy/random/src/philox/LICENSE.md +31 -0
  1038. numpy-2.4.1.dist-info/licenses/numpy/random/src/sfc64/LICENSE.md +27 -0
  1039. numpy-2.4.1.dist-info/licenses/numpy/random/src/splitmix64/LICENSE.md +9 -0
@@ -0,0 +1,3533 @@
1
+ import inspect
2
+ import subprocess
3
+ import sys
4
+ import textwrap
5
+ import warnings
6
+
7
+ import pytest
8
+
9
+ import numpy as np
10
+ import numpy._core._multiarray_tests as _multiarray_tests
11
+ import numpy._core.umath as ncu
12
+ from numpy import all, arange, array, nditer
13
+ from numpy.testing import (
14
+ HAS_REFCOUNT,
15
+ IS_64BIT,
16
+ IS_PYPY,
17
+ IS_WASM,
18
+ assert_,
19
+ assert_array_equal,
20
+ assert_equal,
21
+ assert_raises,
22
+ )
23
+ from numpy.testing._private.utils import requires_memory
24
+
25
+
26
+ def iter_multi_index(i):
27
+ ret = []
28
+ while not i.finished:
29
+ ret.append(i.multi_index)
30
+ i.iternext()
31
+ return ret
32
+
33
+ def iter_indices(i):
34
+ ret = []
35
+ while not i.finished:
36
+ ret.append(i.index)
37
+ i.iternext()
38
+ return ret
39
+
40
+ def iter_iterindices(i):
41
+ ret = []
42
+ while not i.finished:
43
+ ret.append(i.iterindex)
44
+ i.iternext()
45
+ return ret
46
+
47
+ @pytest.mark.skipif(not HAS_REFCOUNT, reason="Python lacks refcounts")
48
+ def test_iter_refcount():
49
+ # Make sure the iterator doesn't leak
50
+
51
+ # Basic
52
+ a = arange(6)
53
+ dt = np.dtype('f4').newbyteorder()
54
+ rc_a = sys.getrefcount(a)
55
+ rc_dt = sys.getrefcount(dt)
56
+ with nditer(a, [],
57
+ [['readwrite', 'updateifcopy']],
58
+ casting='unsafe',
59
+ op_dtypes=[dt]) as it:
60
+ assert_(not it.iterationneedsapi)
61
+ assert_(sys.getrefcount(a) > rc_a)
62
+ assert_(sys.getrefcount(dt) > rc_dt)
63
+ # del 'it'
64
+ it = None
65
+ assert_equal(sys.getrefcount(a), rc_a)
66
+ assert_equal(sys.getrefcount(dt), rc_dt)
67
+
68
+ # With a copy
69
+ a = arange(6, dtype='f4')
70
+ dt = np.dtype('f4')
71
+ rc_a = sys.getrefcount(a)
72
+ rc_dt = sys.getrefcount(dt)
73
+ it = nditer(a, [],
74
+ [['readwrite']],
75
+ op_dtypes=[dt])
76
+ rc2_a = sys.getrefcount(a)
77
+ rc2_dt = sys.getrefcount(dt)
78
+ it2 = it.copy()
79
+ assert_(sys.getrefcount(a) > rc2_a)
80
+ if sys.version_info < (3, 13):
81
+ # np.dtype('f4') is immortal after Python 3.13
82
+ assert_(sys.getrefcount(dt) > rc2_dt)
83
+ it = None
84
+ assert_equal(sys.getrefcount(a), rc2_a)
85
+ assert_equal(sys.getrefcount(dt), rc2_dt)
86
+ it2 = None
87
+ assert_equal(sys.getrefcount(a), rc_a)
88
+ assert_equal(sys.getrefcount(dt), rc_dt)
89
+
90
+ def test_iter_best_order():
91
+ # The iterator should always find the iteration order
92
+ # with increasing memory addresses
93
+
94
+ # Test the ordering for 1-D to 5-D shapes
95
+ for shape in [(5,), (3, 4), (2, 3, 4), (2, 3, 4, 3), (2, 3, 2, 2, 3)]:
96
+ a = arange(np.prod(shape))
97
+ # Test each combination of positive and negative strides
98
+ for dirs in range(2**len(shape)):
99
+ dirs_index = [slice(None)] * len(shape)
100
+ for bit in range(len(shape)):
101
+ if ((2**bit) & dirs):
102
+ dirs_index[bit] = slice(None, None, -1)
103
+ dirs_index = tuple(dirs_index)
104
+
105
+ aview = a.reshape(shape)[dirs_index]
106
+ # C-order
107
+ i = nditer(aview, [], [['readonly']])
108
+ assert_equal(list(i), a)
109
+ # Fortran-order
110
+ i = nditer(aview.T, [], [['readonly']])
111
+ assert_equal(list(i), a)
112
+ # Other order
113
+ if len(shape) > 2:
114
+ i = nditer(aview.swapaxes(0, 1), [], [['readonly']])
115
+ assert_equal(list(i), a)
116
+
117
+ def test_iter_c_order():
118
+ # Test forcing C order
119
+
120
+ # Test the ordering for 1-D to 5-D shapes
121
+ for shape in [(5,), (3, 4), (2, 3, 4), (2, 3, 4, 3), (2, 3, 2, 2, 3)]:
122
+ a = arange(np.prod(shape))
123
+ # Test each combination of positive and negative strides
124
+ for dirs in range(2**len(shape)):
125
+ dirs_index = [slice(None)] * len(shape)
126
+ for bit in range(len(shape)):
127
+ if ((2**bit) & dirs):
128
+ dirs_index[bit] = slice(None, None, -1)
129
+ dirs_index = tuple(dirs_index)
130
+
131
+ aview = a.reshape(shape)[dirs_index]
132
+ # C-order
133
+ i = nditer(aview, order='C')
134
+ assert_equal(list(i), aview.ravel(order='C'))
135
+ # Fortran-order
136
+ i = nditer(aview.T, order='C')
137
+ assert_equal(list(i), aview.T.ravel(order='C'))
138
+ # Other order
139
+ if len(shape) > 2:
140
+ i = nditer(aview.swapaxes(0, 1), order='C')
141
+ assert_equal(list(i),
142
+ aview.swapaxes(0, 1).ravel(order='C'))
143
+
144
+ def test_iter_f_order():
145
+ # Test forcing F order
146
+
147
+ # Test the ordering for 1-D to 5-D shapes
148
+ for shape in [(5,), (3, 4), (2, 3, 4), (2, 3, 4, 3), (2, 3, 2, 2, 3)]:
149
+ a = arange(np.prod(shape))
150
+ # Test each combination of positive and negative strides
151
+ for dirs in range(2**len(shape)):
152
+ dirs_index = [slice(None)] * len(shape)
153
+ for bit in range(len(shape)):
154
+ if ((2**bit) & dirs):
155
+ dirs_index[bit] = slice(None, None, -1)
156
+ dirs_index = tuple(dirs_index)
157
+
158
+ aview = a.reshape(shape)[dirs_index]
159
+ # C-order
160
+ i = nditer(aview, order='F')
161
+ assert_equal(list(i), aview.ravel(order='F'))
162
+ # Fortran-order
163
+ i = nditer(aview.T, order='F')
164
+ assert_equal(list(i), aview.T.ravel(order='F'))
165
+ # Other order
166
+ if len(shape) > 2:
167
+ i = nditer(aview.swapaxes(0, 1), order='F')
168
+ assert_equal(list(i),
169
+ aview.swapaxes(0, 1).ravel(order='F'))
170
+
171
+ def test_iter_c_or_f_order():
172
+ # Test forcing any contiguous (C or F) order
173
+
174
+ # Test the ordering for 1-D to 5-D shapes
175
+ for shape in [(5,), (3, 4), (2, 3, 4), (2, 3, 4, 3), (2, 3, 2, 2, 3)]:
176
+ a = arange(np.prod(shape))
177
+ # Test each combination of positive and negative strides
178
+ for dirs in range(2**len(shape)):
179
+ dirs_index = [slice(None)] * len(shape)
180
+ for bit in range(len(shape)):
181
+ if ((2**bit) & dirs):
182
+ dirs_index[bit] = slice(None, None, -1)
183
+ dirs_index = tuple(dirs_index)
184
+
185
+ aview = a.reshape(shape)[dirs_index]
186
+ # C-order
187
+ i = nditer(aview, order='A')
188
+ assert_equal(list(i), aview.ravel(order='A'))
189
+ # Fortran-order
190
+ i = nditer(aview.T, order='A')
191
+ assert_equal(list(i), aview.T.ravel(order='A'))
192
+ # Other order
193
+ if len(shape) > 2:
194
+ i = nditer(aview.swapaxes(0, 1), order='A')
195
+ assert_equal(list(i),
196
+ aview.swapaxes(0, 1).ravel(order='A'))
197
+
198
+ def test_nditer_multi_index_set():
199
+ # Test the multi_index set
200
+ a = np.arange(6).reshape(2, 3)
201
+ it = np.nditer(a, flags=['multi_index'])
202
+
203
+ # Removes the iteration on two first elements of a[0]
204
+ it.multi_index = (0, 2,)
205
+
206
+ assert_equal(list(it), [2, 3, 4, 5])
207
+
208
+ @pytest.mark.skipif(not HAS_REFCOUNT, reason="Python lacks refcounts")
209
+ def test_nditer_multi_index_set_refcount():
210
+ # Test if the reference count on index variable is decreased
211
+
212
+ index = 0
213
+ i = np.nditer(np.array([111, 222, 333, 444]), flags=['multi_index'])
214
+
215
+ start_count = sys.getrefcount(index)
216
+ i.multi_index = (index,)
217
+ end_count = sys.getrefcount(index)
218
+
219
+ assert_equal(start_count, end_count)
220
+
221
+ def test_iter_best_order_multi_index_1d():
222
+ # The multi-indices should be correct with any reordering
223
+
224
+ a = arange(4)
225
+ # 1D order
226
+ i = nditer(a, ['multi_index'], [['readonly']])
227
+ assert_equal(iter_multi_index(i), [(0,), (1,), (2,), (3,)])
228
+ # 1D reversed order
229
+ i = nditer(a[::-1], ['multi_index'], [['readonly']])
230
+ assert_equal(iter_multi_index(i), [(3,), (2,), (1,), (0,)])
231
+
232
+ def test_iter_best_order_multi_index_2d():
233
+ # The multi-indices should be correct with any reordering
234
+
235
+ a = arange(6)
236
+ # 2D C-order
237
+ i = nditer(a.reshape(2, 3), ['multi_index'], [['readonly']])
238
+ assert_equal(iter_multi_index(i), [(0, 0), (0, 1), (0, 2), (1, 0), (1, 1), (1, 2)])
239
+ # 2D Fortran-order
240
+ i = nditer(a.reshape(2, 3).copy(order='F'), ['multi_index'], [['readonly']])
241
+ assert_equal(iter_multi_index(i), [(0, 0), (1, 0), (0, 1), (1, 1), (0, 2), (1, 2)])
242
+ # 2D reversed C-order
243
+ i = nditer(a.reshape(2, 3)[::-1], ['multi_index'], [['readonly']])
244
+ assert_equal(iter_multi_index(i), [(1, 0), (1, 1), (1, 2), (0, 0), (0, 1), (0, 2)])
245
+ i = nditer(a.reshape(2, 3)[:, ::-1], ['multi_index'], [['readonly']])
246
+ assert_equal(iter_multi_index(i), [(0, 2), (0, 1), (0, 0), (1, 2), (1, 1), (1, 0)])
247
+ i = nditer(a.reshape(2, 3)[::-1, ::-1], ['multi_index'], [['readonly']])
248
+ assert_equal(iter_multi_index(i), [(1, 2), (1, 1), (1, 0), (0, 2), (0, 1), (0, 0)])
249
+ # 2D reversed Fortran-order
250
+ i = nditer(a.reshape(2, 3).copy(order='F')[::-1], ['multi_index'], [['readonly']])
251
+ assert_equal(iter_multi_index(i), [(1, 0), (0, 0), (1, 1), (0, 1), (1, 2), (0, 2)])
252
+ i = nditer(a.reshape(2, 3).copy(order='F')[:, ::-1],
253
+ ['multi_index'], [['readonly']])
254
+ assert_equal(iter_multi_index(i), [(0, 2), (1, 2), (0, 1), (1, 1), (0, 0), (1, 0)])
255
+ i = nditer(a.reshape(2, 3).copy(order='F')[::-1, ::-1],
256
+ ['multi_index'], [['readonly']])
257
+ assert_equal(iter_multi_index(i), [(1, 2), (0, 2), (1, 1), (0, 1), (1, 0), (0, 0)])
258
+
259
+ def test_iter_best_order_multi_index_3d():
260
+ # The multi-indices should be correct with any reordering
261
+
262
+ a = arange(12)
263
+ # 3D C-order
264
+ i = nditer(a.reshape(2, 3, 2), ['multi_index'], [['readonly']])
265
+ assert_equal(iter_multi_index(i),
266
+ [(0, 0, 0), (0, 0, 1), (0, 1, 0), (0, 1, 1), (0, 2, 0), (0, 2, 1),
267
+ (1, 0, 0), (1, 0, 1), (1, 1, 0), (1, 1, 1), (1, 2, 0), (1, 2, 1)])
268
+ # 3D Fortran-order
269
+ i = nditer(a.reshape(2, 3, 2).copy(order='F'), ['multi_index'], [['readonly']])
270
+ assert_equal(iter_multi_index(i),
271
+ [(0, 0, 0), (1, 0, 0), (0, 1, 0), (1, 1, 0), (0, 2, 0), (1, 2, 0),
272
+ (0, 0, 1), (1, 0, 1), (0, 1, 1), (1, 1, 1), (0, 2, 1), (1, 2, 1)])
273
+ # 3D reversed C-order
274
+ i = nditer(a.reshape(2, 3, 2)[::-1], ['multi_index'], [['readonly']])
275
+ assert_equal(iter_multi_index(i),
276
+ [(1, 0, 0), (1, 0, 1), (1, 1, 0), (1, 1, 1), (1, 2, 0), (1, 2, 1),
277
+ (0, 0, 0), (0, 0, 1), (0, 1, 0), (0, 1, 1), (0, 2, 0), (0, 2, 1)])
278
+ i = nditer(a.reshape(2, 3, 2)[:, ::-1], ['multi_index'], [['readonly']])
279
+ assert_equal(iter_multi_index(i),
280
+ [(0, 2, 0), (0, 2, 1), (0, 1, 0), (0, 1, 1), (0, 0, 0), (0, 0, 1),
281
+ (1, 2, 0), (1, 2, 1), (1, 1, 0), (1, 1, 1), (1, 0, 0), (1, 0, 1)])
282
+ i = nditer(a.reshape(2, 3, 2)[:, :, ::-1], ['multi_index'], [['readonly']])
283
+ assert_equal(iter_multi_index(i),
284
+ [(0, 0, 1), (0, 0, 0), (0, 1, 1), (0, 1, 0), (0, 2, 1), (0, 2, 0),
285
+ (1, 0, 1), (1, 0, 0), (1, 1, 1), (1, 1, 0), (1, 2, 1), (1, 2, 0)])
286
+ # 3D reversed Fortran-order
287
+ i = nditer(a.reshape(2, 3, 2).copy(order='F')[::-1],
288
+ ['multi_index'], [['readonly']])
289
+ assert_equal(iter_multi_index(i),
290
+ [(1, 0, 0), (0, 0, 0), (1, 1, 0), (0, 1, 0), (1, 2, 0), (0, 2, 0),
291
+ (1, 0, 1), (0, 0, 1), (1, 1, 1), (0, 1, 1), (1, 2, 1), (0, 2, 1)])
292
+ i = nditer(a.reshape(2, 3, 2).copy(order='F')[:, ::-1],
293
+ ['multi_index'], [['readonly']])
294
+ assert_equal(iter_multi_index(i),
295
+ [(0, 2, 0), (1, 2, 0), (0, 1, 0), (1, 1, 0), (0, 0, 0), (1, 0, 0),
296
+ (0, 2, 1), (1, 2, 1), (0, 1, 1), (1, 1, 1), (0, 0, 1), (1, 0, 1)])
297
+ i = nditer(a.reshape(2, 3, 2).copy(order='F')[:, :, ::-1],
298
+ ['multi_index'], [['readonly']])
299
+ assert_equal(iter_multi_index(i),
300
+ [(0, 0, 1), (1, 0, 1), (0, 1, 1), (1, 1, 1), (0, 2, 1), (1, 2, 1),
301
+ (0, 0, 0), (1, 0, 0), (0, 1, 0), (1, 1, 0), (0, 2, 0), (1, 2, 0)])
302
+
303
+ def test_iter_best_order_c_index_1d():
304
+ # The C index should be correct with any reordering
305
+
306
+ a = arange(4)
307
+ # 1D order
308
+ i = nditer(a, ['c_index'], [['readonly']])
309
+ assert_equal(iter_indices(i), [0, 1, 2, 3])
310
+ # 1D reversed order
311
+ i = nditer(a[::-1], ['c_index'], [['readonly']])
312
+ assert_equal(iter_indices(i), [3, 2, 1, 0])
313
+
314
+ def test_iter_best_order_c_index_2d():
315
+ # The C index should be correct with any reordering
316
+
317
+ a = arange(6)
318
+ # 2D C-order
319
+ i = nditer(a.reshape(2, 3), ['c_index'], [['readonly']])
320
+ assert_equal(iter_indices(i), [0, 1, 2, 3, 4, 5])
321
+ # 2D Fortran-order
322
+ i = nditer(a.reshape(2, 3).copy(order='F'),
323
+ ['c_index'], [['readonly']])
324
+ assert_equal(iter_indices(i), [0, 3, 1, 4, 2, 5])
325
+ # 2D reversed C-order
326
+ i = nditer(a.reshape(2, 3)[::-1], ['c_index'], [['readonly']])
327
+ assert_equal(iter_indices(i), [3, 4, 5, 0, 1, 2])
328
+ i = nditer(a.reshape(2, 3)[:, ::-1], ['c_index'], [['readonly']])
329
+ assert_equal(iter_indices(i), [2, 1, 0, 5, 4, 3])
330
+ i = nditer(a.reshape(2, 3)[::-1, ::-1], ['c_index'], [['readonly']])
331
+ assert_equal(iter_indices(i), [5, 4, 3, 2, 1, 0])
332
+ # 2D reversed Fortran-order
333
+ i = nditer(a.reshape(2, 3).copy(order='F')[::-1],
334
+ ['c_index'], [['readonly']])
335
+ assert_equal(iter_indices(i), [3, 0, 4, 1, 5, 2])
336
+ i = nditer(a.reshape(2, 3).copy(order='F')[:, ::-1],
337
+ ['c_index'], [['readonly']])
338
+ assert_equal(iter_indices(i), [2, 5, 1, 4, 0, 3])
339
+ i = nditer(a.reshape(2, 3).copy(order='F')[::-1, ::-1],
340
+ ['c_index'], [['readonly']])
341
+ assert_equal(iter_indices(i), [5, 2, 4, 1, 3, 0])
342
+
343
+ def test_iter_best_order_c_index_3d():
344
+ # The C index should be correct with any reordering
345
+
346
+ a = arange(12)
347
+ # 3D C-order
348
+ i = nditer(a.reshape(2, 3, 2), ['c_index'], [['readonly']])
349
+ assert_equal(iter_indices(i),
350
+ [0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11])
351
+ # 3D Fortran-order
352
+ i = nditer(a.reshape(2, 3, 2).copy(order='F'),
353
+ ['c_index'], [['readonly']])
354
+ assert_equal(iter_indices(i),
355
+ [0, 6, 2, 8, 4, 10, 1, 7, 3, 9, 5, 11])
356
+ # 3D reversed C-order
357
+ i = nditer(a.reshape(2, 3, 2)[::-1], ['c_index'], [['readonly']])
358
+ assert_equal(iter_indices(i),
359
+ [6, 7, 8, 9, 10, 11, 0, 1, 2, 3, 4, 5])
360
+ i = nditer(a.reshape(2, 3, 2)[:, ::-1], ['c_index'], [['readonly']])
361
+ assert_equal(iter_indices(i),
362
+ [4, 5, 2, 3, 0, 1, 10, 11, 8, 9, 6, 7])
363
+ i = nditer(a.reshape(2, 3, 2)[:, :, ::-1], ['c_index'], [['readonly']])
364
+ assert_equal(iter_indices(i),
365
+ [1, 0, 3, 2, 5, 4, 7, 6, 9, 8, 11, 10])
366
+ # 3D reversed Fortran-order
367
+ i = nditer(a.reshape(2, 3, 2).copy(order='F')[::-1],
368
+ ['c_index'], [['readonly']])
369
+ assert_equal(iter_indices(i),
370
+ [6, 0, 8, 2, 10, 4, 7, 1, 9, 3, 11, 5])
371
+ i = nditer(a.reshape(2, 3, 2).copy(order='F')[:, ::-1],
372
+ ['c_index'], [['readonly']])
373
+ assert_equal(iter_indices(i),
374
+ [4, 10, 2, 8, 0, 6, 5, 11, 3, 9, 1, 7])
375
+ i = nditer(a.reshape(2, 3, 2).copy(order='F')[:, :, ::-1],
376
+ ['c_index'], [['readonly']])
377
+ assert_equal(iter_indices(i),
378
+ [1, 7, 3, 9, 5, 11, 0, 6, 2, 8, 4, 10])
379
+
380
+ def test_iter_best_order_f_index_1d():
381
+ # The Fortran index should be correct with any reordering
382
+
383
+ a = arange(4)
384
+ # 1D order
385
+ i = nditer(a, ['f_index'], [['readonly']])
386
+ assert_equal(iter_indices(i), [0, 1, 2, 3])
387
+ # 1D reversed order
388
+ i = nditer(a[::-1], ['f_index'], [['readonly']])
389
+ assert_equal(iter_indices(i), [3, 2, 1, 0])
390
+
391
+ def test_iter_best_order_f_index_2d():
392
+ # The Fortran index should be correct with any reordering
393
+
394
+ a = arange(6)
395
+ # 2D C-order
396
+ i = nditer(a.reshape(2, 3), ['f_index'], [['readonly']])
397
+ assert_equal(iter_indices(i), [0, 2, 4, 1, 3, 5])
398
+ # 2D Fortran-order
399
+ i = nditer(a.reshape(2, 3).copy(order='F'),
400
+ ['f_index'], [['readonly']])
401
+ assert_equal(iter_indices(i), [0, 1, 2, 3, 4, 5])
402
+ # 2D reversed C-order
403
+ i = nditer(a.reshape(2, 3)[::-1], ['f_index'], [['readonly']])
404
+ assert_equal(iter_indices(i), [1, 3, 5, 0, 2, 4])
405
+ i = nditer(a.reshape(2, 3)[:, ::-1], ['f_index'], [['readonly']])
406
+ assert_equal(iter_indices(i), [4, 2, 0, 5, 3, 1])
407
+ i = nditer(a.reshape(2, 3)[::-1, ::-1], ['f_index'], [['readonly']])
408
+ assert_equal(iter_indices(i), [5, 3, 1, 4, 2, 0])
409
+ # 2D reversed Fortran-order
410
+ i = nditer(a.reshape(2, 3).copy(order='F')[::-1],
411
+ ['f_index'], [['readonly']])
412
+ assert_equal(iter_indices(i), [1, 0, 3, 2, 5, 4])
413
+ i = nditer(a.reshape(2, 3).copy(order='F')[:, ::-1],
414
+ ['f_index'], [['readonly']])
415
+ assert_equal(iter_indices(i), [4, 5, 2, 3, 0, 1])
416
+ i = nditer(a.reshape(2, 3).copy(order='F')[::-1, ::-1],
417
+ ['f_index'], [['readonly']])
418
+ assert_equal(iter_indices(i), [5, 4, 3, 2, 1, 0])
419
+
420
+ def test_iter_best_order_f_index_3d():
421
+ # The Fortran index should be correct with any reordering
422
+
423
+ a = arange(12)
424
+ # 3D C-order
425
+ i = nditer(a.reshape(2, 3, 2), ['f_index'], [['readonly']])
426
+ assert_equal(iter_indices(i),
427
+ [0, 6, 2, 8, 4, 10, 1, 7, 3, 9, 5, 11])
428
+ # 3D Fortran-order
429
+ i = nditer(a.reshape(2, 3, 2).copy(order='F'),
430
+ ['f_index'], [['readonly']])
431
+ assert_equal(iter_indices(i),
432
+ [0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11])
433
+ # 3D reversed C-order
434
+ i = nditer(a.reshape(2, 3, 2)[::-1], ['f_index'], [['readonly']])
435
+ assert_equal(iter_indices(i),
436
+ [1, 7, 3, 9, 5, 11, 0, 6, 2, 8, 4, 10])
437
+ i = nditer(a.reshape(2, 3, 2)[:, ::-1], ['f_index'], [['readonly']])
438
+ assert_equal(iter_indices(i),
439
+ [4, 10, 2, 8, 0, 6, 5, 11, 3, 9, 1, 7])
440
+ i = nditer(a.reshape(2, 3, 2)[:, :, ::-1], ['f_index'], [['readonly']])
441
+ assert_equal(iter_indices(i),
442
+ [6, 0, 8, 2, 10, 4, 7, 1, 9, 3, 11, 5])
443
+ # 3D reversed Fortran-order
444
+ i = nditer(a.reshape(2, 3, 2).copy(order='F')[::-1],
445
+ ['f_index'], [['readonly']])
446
+ assert_equal(iter_indices(i),
447
+ [1, 0, 3, 2, 5, 4, 7, 6, 9, 8, 11, 10])
448
+ i = nditer(a.reshape(2, 3, 2).copy(order='F')[:, ::-1],
449
+ ['f_index'], [['readonly']])
450
+ assert_equal(iter_indices(i),
451
+ [4, 5, 2, 3, 0, 1, 10, 11, 8, 9, 6, 7])
452
+ i = nditer(a.reshape(2, 3, 2).copy(order='F')[:, :, ::-1],
453
+ ['f_index'], [['readonly']])
454
+ assert_equal(iter_indices(i),
455
+ [6, 7, 8, 9, 10, 11, 0, 1, 2, 3, 4, 5])
456
+
457
+ def test_iter_no_inner_full_coalesce():
458
+ # Check no_inner iterators which coalesce into a single inner loop
459
+
460
+ for shape in [(5,), (3, 4), (2, 3, 4), (2, 3, 4, 3), (2, 3, 2, 2, 3)]:
461
+ size = np.prod(shape)
462
+ a = arange(size)
463
+ # Test each combination of forward and backwards indexing
464
+ for dirs in range(2**len(shape)):
465
+ dirs_index = [slice(None)] * len(shape)
466
+ for bit in range(len(shape)):
467
+ if ((2**bit) & dirs):
468
+ dirs_index[bit] = slice(None, None, -1)
469
+ dirs_index = tuple(dirs_index)
470
+
471
+ aview = a.reshape(shape)[dirs_index]
472
+ # C-order
473
+ i = nditer(aview, ['external_loop'], [['readonly']])
474
+ assert_equal(i.ndim, 1)
475
+ assert_equal(i[0].shape, (size,))
476
+ # Fortran-order
477
+ i = nditer(aview.T, ['external_loop'], [['readonly']])
478
+ assert_equal(i.ndim, 1)
479
+ assert_equal(i[0].shape, (size,))
480
+ # Other order
481
+ if len(shape) > 2:
482
+ i = nditer(aview.swapaxes(0, 1),
483
+ ['external_loop'], [['readonly']])
484
+ assert_equal(i.ndim, 1)
485
+ assert_equal(i[0].shape, (size,))
486
+
487
+ def test_iter_no_inner_dim_coalescing():
488
+ # Check no_inner iterators whose dimensions may not coalesce completely
489
+
490
+ # Skipping the last element in a dimension prevents coalescing
491
+ # with the next-bigger dimension
492
+ a = arange(24).reshape(2, 3, 4)[:, :, :-1]
493
+ i = nditer(a, ['external_loop'], [['readonly']])
494
+ assert_equal(i.ndim, 2)
495
+ assert_equal(i[0].shape, (3,))
496
+ a = arange(24).reshape(2, 3, 4)[:, :-1, :]
497
+ i = nditer(a, ['external_loop'], [['readonly']])
498
+ assert_equal(i.ndim, 2)
499
+ assert_equal(i[0].shape, (8,))
500
+ a = arange(24).reshape(2, 3, 4)[:-1, :, :]
501
+ i = nditer(a, ['external_loop'], [['readonly']])
502
+ assert_equal(i.ndim, 1)
503
+ assert_equal(i[0].shape, (12,))
504
+
505
+ # Even with lots of 1-sized dimensions, should still coalesce
506
+ a = arange(24).reshape(1, 1, 2, 1, 1, 3, 1, 1, 4, 1, 1)
507
+ i = nditer(a, ['external_loop'], [['readonly']])
508
+ assert_equal(i.ndim, 1)
509
+ assert_equal(i[0].shape, (24,))
510
+
511
+ def test_iter_dim_coalescing():
512
+ # Check that the correct number of dimensions are coalesced
513
+
514
+ # Tracking a multi-index disables coalescing
515
+ a = arange(24).reshape(2, 3, 4)
516
+ i = nditer(a, ['multi_index'], [['readonly']])
517
+ assert_equal(i.ndim, 3)
518
+
519
+ # A tracked index can allow coalescing if it's compatible with the array
520
+ a3d = arange(24).reshape(2, 3, 4)
521
+ i = nditer(a3d, ['c_index'], [['readonly']])
522
+ assert_equal(i.ndim, 1)
523
+ i = nditer(a3d.swapaxes(0, 1), ['c_index'], [['readonly']])
524
+ assert_equal(i.ndim, 3)
525
+ i = nditer(a3d.T, ['c_index'], [['readonly']])
526
+ assert_equal(i.ndim, 3)
527
+ i = nditer(a3d.T, ['f_index'], [['readonly']])
528
+ assert_equal(i.ndim, 1)
529
+ i = nditer(a3d.T.swapaxes(0, 1), ['f_index'], [['readonly']])
530
+ assert_equal(i.ndim, 3)
531
+
532
+ # When C or F order is forced, coalescing may still occur
533
+ a3d = arange(24).reshape(2, 3, 4)
534
+ i = nditer(a3d, order='C')
535
+ assert_equal(i.ndim, 1)
536
+ i = nditer(a3d.T, order='C')
537
+ assert_equal(i.ndim, 3)
538
+ i = nditer(a3d, order='F')
539
+ assert_equal(i.ndim, 3)
540
+ i = nditer(a3d.T, order='F')
541
+ assert_equal(i.ndim, 1)
542
+ i = nditer(a3d, order='A')
543
+ assert_equal(i.ndim, 1)
544
+ i = nditer(a3d.T, order='A')
545
+ assert_equal(i.ndim, 1)
546
+
547
+ def test_iter_broadcasting():
548
+ # Standard NumPy broadcasting rules
549
+
550
+ # 1D with scalar
551
+ i = nditer([arange(6), np.int32(2)], ['multi_index'], [['readonly']] * 2)
552
+ assert_equal(i.itersize, 6)
553
+ assert_equal(i.shape, (6,))
554
+
555
+ # 2D with scalar
556
+ i = nditer([arange(6).reshape(2, 3), np.int32(2)],
557
+ ['multi_index'], [['readonly']] * 2)
558
+ assert_equal(i.itersize, 6)
559
+ assert_equal(i.shape, (2, 3))
560
+ # 2D with 1D
561
+ i = nditer([arange(6).reshape(2, 3), arange(3)],
562
+ ['multi_index'], [['readonly']] * 2)
563
+ assert_equal(i.itersize, 6)
564
+ assert_equal(i.shape, (2, 3))
565
+ i = nditer([arange(2).reshape(2, 1), arange(3)],
566
+ ['multi_index'], [['readonly']] * 2)
567
+ assert_equal(i.itersize, 6)
568
+ assert_equal(i.shape, (2, 3))
569
+ # 2D with 2D
570
+ i = nditer([arange(2).reshape(2, 1), arange(3).reshape(1, 3)],
571
+ ['multi_index'], [['readonly']] * 2)
572
+ assert_equal(i.itersize, 6)
573
+ assert_equal(i.shape, (2, 3))
574
+
575
+ # 3D with scalar
576
+ i = nditer([np.int32(2), arange(24).reshape(4, 2, 3)],
577
+ ['multi_index'], [['readonly']] * 2)
578
+ assert_equal(i.itersize, 24)
579
+ assert_equal(i.shape, (4, 2, 3))
580
+ # 3D with 1D
581
+ i = nditer([arange(3), arange(24).reshape(4, 2, 3)],
582
+ ['multi_index'], [['readonly']] * 2)
583
+ assert_equal(i.itersize, 24)
584
+ assert_equal(i.shape, (4, 2, 3))
585
+ i = nditer([arange(3), arange(8).reshape(4, 2, 1)],
586
+ ['multi_index'], [['readonly']] * 2)
587
+ assert_equal(i.itersize, 24)
588
+ assert_equal(i.shape, (4, 2, 3))
589
+ # 3D with 2D
590
+ i = nditer([arange(6).reshape(2, 3), arange(24).reshape(4, 2, 3)],
591
+ ['multi_index'], [['readonly']] * 2)
592
+ assert_equal(i.itersize, 24)
593
+ assert_equal(i.shape, (4, 2, 3))
594
+ i = nditer([arange(2).reshape(2, 1), arange(24).reshape(4, 2, 3)],
595
+ ['multi_index'], [['readonly']] * 2)
596
+ assert_equal(i.itersize, 24)
597
+ assert_equal(i.shape, (4, 2, 3))
598
+ i = nditer([arange(3).reshape(1, 3), arange(8).reshape(4, 2, 1)],
599
+ ['multi_index'], [['readonly']] * 2)
600
+ assert_equal(i.itersize, 24)
601
+ assert_equal(i.shape, (4, 2, 3))
602
+ # 3D with 3D
603
+ i = nditer([arange(2).reshape(1, 2, 1), arange(3).reshape(1, 1, 3),
604
+ arange(4).reshape(4, 1, 1)],
605
+ ['multi_index'], [['readonly']] * 3)
606
+ assert_equal(i.itersize, 24)
607
+ assert_equal(i.shape, (4, 2, 3))
608
+ i = nditer([arange(6).reshape(1, 2, 3), arange(4).reshape(4, 1, 1)],
609
+ ['multi_index'], [['readonly']] * 2)
610
+ assert_equal(i.itersize, 24)
611
+ assert_equal(i.shape, (4, 2, 3))
612
+ i = nditer([arange(24).reshape(4, 2, 3), arange(12).reshape(4, 1, 3)],
613
+ ['multi_index'], [['readonly']] * 2)
614
+ assert_equal(i.itersize, 24)
615
+ assert_equal(i.shape, (4, 2, 3))
616
+
617
+ def test_iter_itershape():
618
+ # Check that allocated outputs work with a specified shape
619
+ a = np.arange(6, dtype='i2').reshape(2, 3)
620
+ i = nditer([a, None], [], [['readonly'], ['writeonly', 'allocate']],
621
+ op_axes=[[0, 1, None], None],
622
+ itershape=(-1, -1, 4))
623
+ assert_equal(i.operands[1].shape, (2, 3, 4))
624
+ assert_equal(i.operands[1].strides, (24, 8, 2))
625
+
626
+ i = nditer([a.T, None], [], [['readonly'], ['writeonly', 'allocate']],
627
+ op_axes=[[0, 1, None], None],
628
+ itershape=(-1, -1, 4))
629
+ assert_equal(i.operands[1].shape, (3, 2, 4))
630
+ assert_equal(i.operands[1].strides, (8, 24, 2))
631
+
632
+ i = nditer([a.T, None], [], [['readonly'], ['writeonly', 'allocate']],
633
+ order='F',
634
+ op_axes=[[0, 1, None], None],
635
+ itershape=(-1, -1, 4))
636
+ assert_equal(i.operands[1].shape, (3, 2, 4))
637
+ assert_equal(i.operands[1].strides, (2, 6, 12))
638
+
639
+ # If we specify 1 in the itershape, it shouldn't allow broadcasting
640
+ # of that dimension to a bigger value
641
+ assert_raises(ValueError, nditer, [a, None], [],
642
+ [['readonly'], ['writeonly', 'allocate']],
643
+ op_axes=[[0, 1, None], None],
644
+ itershape=(-1, 1, 4))
645
+ # Test bug that for no op_axes but itershape, they are NULLed correctly
646
+ i = np.nditer([np.ones(2), None, None], itershape=(2,))
647
+
648
+ def test_iter_broadcasting_errors():
649
+ # Check that errors are thrown for bad broadcasting shapes
650
+
651
+ # 1D with 1D
652
+ assert_raises(ValueError, nditer, [arange(2), arange(3)],
653
+ [], [['readonly']] * 2)
654
+ # 2D with 1D
655
+ assert_raises(ValueError, nditer,
656
+ [arange(6).reshape(2, 3), arange(2)],
657
+ [], [['readonly']] * 2)
658
+ # 2D with 2D
659
+ assert_raises(ValueError, nditer,
660
+ [arange(6).reshape(2, 3), arange(9).reshape(3, 3)],
661
+ [], [['readonly']] * 2)
662
+ assert_raises(ValueError, nditer,
663
+ [arange(6).reshape(2, 3), arange(4).reshape(2, 2)],
664
+ [], [['readonly']] * 2)
665
+ # 3D with 3D
666
+ assert_raises(ValueError, nditer,
667
+ [arange(36).reshape(3, 3, 4), arange(24).reshape(2, 3, 4)],
668
+ [], [['readonly']] * 2)
669
+ assert_raises(ValueError, nditer,
670
+ [arange(8).reshape(2, 4, 1), arange(24).reshape(2, 3, 4)],
671
+ [], [['readonly']] * 2)
672
+
673
+ # Verify that the error message mentions the right shapes
674
+ try:
675
+ nditer([arange(2).reshape(1, 2, 1),
676
+ arange(3).reshape(1, 3),
677
+ arange(6).reshape(2, 3)],
678
+ [],
679
+ [['readonly'], ['readonly'], ['writeonly', 'no_broadcast']])
680
+ raise AssertionError('Should have raised a broadcast error')
681
+ except ValueError as e:
682
+ msg = str(e)
683
+ # The message should contain the shape of the 3rd operand
684
+ assert_(msg.find('(2,3)') >= 0,
685
+ f'Message "{msg}" doesn\'t contain operand shape (2,3)')
686
+ # The message should contain the broadcast shape
687
+ assert_(msg.find('(1,2,3)') >= 0,
688
+ f'Message "{msg}" doesn\'t contain broadcast shape (1,2,3)')
689
+
690
+ try:
691
+ nditer([arange(6).reshape(2, 3), arange(2)],
692
+ [],
693
+ [['readonly'], ['readonly']],
694
+ op_axes=[[0, 1], [0, np.newaxis]],
695
+ itershape=(4, 3))
696
+ raise AssertionError('Should have raised a broadcast error')
697
+ except ValueError as e:
698
+ msg = str(e)
699
+ # The message should contain "shape->remappedshape" for each operand
700
+ assert_(msg.find('(2,3)->(2,3)') >= 0,
701
+ f'Message "{msg}" doesn\'t contain operand shape (2,3)->(2,3)')
702
+ assert_(msg.find('(2,)->(2,newaxis)') >= 0,
703
+ ('Message "%s" doesn\'t contain remapped operand shape'
704
+ '(2,)->(2,newaxis)') % msg)
705
+ # The message should contain the itershape parameter
706
+ assert_(msg.find('(4,3)') >= 0,
707
+ f'Message "{msg}" doesn\'t contain itershape parameter (4,3)')
708
+
709
+ try:
710
+ nditer([np.zeros((2, 1, 1)), np.zeros((2,))],
711
+ [],
712
+ [['writeonly', 'no_broadcast'], ['readonly']])
713
+ raise AssertionError('Should have raised a broadcast error')
714
+ except ValueError as e:
715
+ msg = str(e)
716
+ # The message should contain the shape of the bad operand
717
+ assert_(msg.find('(2,1,1)') >= 0,
718
+ f'Message "{msg}" doesn\'t contain operand shape (2,1,1)')
719
+ # The message should contain the broadcast shape
720
+ assert_(msg.find('(2,1,2)') >= 0,
721
+ f'Message "{msg}" doesn\'t contain the broadcast shape (2,1,2)')
722
+
723
+ def test_iter_flags_errors():
724
+ # Check that bad combinations of flags produce errors
725
+
726
+ a = arange(6)
727
+
728
+ # Not enough operands
729
+ assert_raises(ValueError, nditer, [], [], [])
730
+ # Bad global flag
731
+ assert_raises(ValueError, nditer, [a], ['bad flag'], [['readonly']])
732
+ # Bad op flag
733
+ assert_raises(ValueError, nditer, [a], [], [['readonly', 'bad flag']])
734
+ # Bad order parameter
735
+ assert_raises(ValueError, nditer, [a], [], [['readonly']], order='G')
736
+ # Bad casting parameter
737
+ assert_raises(ValueError, nditer, [a], [], [['readonly']], casting='noon')
738
+ # op_flags must match ops
739
+ assert_raises(ValueError, nditer, [a] * 3, [], [['readonly']] * 2)
740
+ # Cannot track both a C and an F index
741
+ assert_raises(ValueError, nditer, a,
742
+ ['c_index', 'f_index'], [['readonly']])
743
+ # Inner iteration and multi-indices/indices are incompatible
744
+ assert_raises(ValueError, nditer, a,
745
+ ['external_loop', 'multi_index'], [['readonly']])
746
+ assert_raises(ValueError, nditer, a,
747
+ ['external_loop', 'c_index'], [['readonly']])
748
+ assert_raises(ValueError, nditer, a,
749
+ ['external_loop', 'f_index'], [['readonly']])
750
+ # Must specify exactly one of readwrite/readonly/writeonly per operand
751
+ assert_raises(ValueError, nditer, a, [], [[]])
752
+ assert_raises(ValueError, nditer, a, [], [['readonly', 'writeonly']])
753
+ assert_raises(ValueError, nditer, a, [], [['readonly', 'readwrite']])
754
+ assert_raises(ValueError, nditer, a, [], [['writeonly', 'readwrite']])
755
+ assert_raises(ValueError, nditer, a,
756
+ [], [['readonly', 'writeonly', 'readwrite']])
757
+ # Python scalars are always readonly
758
+ assert_raises(TypeError, nditer, 1.5, [], [['writeonly']])
759
+ assert_raises(TypeError, nditer, 1.5, [], [['readwrite']])
760
+ # Array scalars are always readonly
761
+ assert_raises(TypeError, nditer, np.int32(1), [], [['writeonly']])
762
+ assert_raises(TypeError, nditer, np.int32(1), [], [['readwrite']])
763
+ # Check readonly array
764
+ a.flags.writeable = False
765
+ assert_raises(ValueError, nditer, a, [], [['writeonly']])
766
+ assert_raises(ValueError, nditer, a, [], [['readwrite']])
767
+ a.flags.writeable = True
768
+ # Multi-indices available only with the multi_index flag
769
+ i = nditer(arange(6), [], [['readonly']])
770
+ assert_raises(ValueError, lambda i: i.multi_index, i)
771
+ # Index available only with an index flag
772
+ assert_raises(ValueError, lambda i: i.index, i)
773
+ # GotoCoords and GotoIndex incompatible with buffering or no_inner
774
+
775
+ def assign_multi_index(i):
776
+ i.multi_index = (0,)
777
+
778
+ def assign_index(i):
779
+ i.index = 0
780
+
781
+ def assign_iterindex(i):
782
+ i.iterindex = 0
783
+
784
+ def assign_iterrange(i):
785
+ i.iterrange = (0, 1)
786
+ i = nditer(arange(6), ['external_loop'])
787
+ assert_raises(ValueError, assign_multi_index, i)
788
+ assert_raises(ValueError, assign_index, i)
789
+ assert_raises(ValueError, assign_iterindex, i)
790
+ assert_raises(ValueError, assign_iterrange, i)
791
+ i = nditer(arange(6), ['buffered'])
792
+ assert_raises(ValueError, assign_multi_index, i)
793
+ assert_raises(ValueError, assign_index, i)
794
+ assert_raises(ValueError, assign_iterrange, i)
795
+ # Can't iterate if size is zero
796
+ assert_raises(ValueError, nditer, np.array([]))
797
+
798
+ def test_iter_slice():
799
+ a, b, c = np.arange(3), np.arange(3), np.arange(3.)
800
+ i = nditer([a, b, c], [], ['readwrite'])
801
+ with i:
802
+ i[0:2] = (3, 3)
803
+ assert_equal(a, [3, 1, 2])
804
+ assert_equal(b, [3, 1, 2])
805
+ assert_equal(c, [0, 1, 2])
806
+ i[1] = 12
807
+ assert_equal(i[0:2], [3, 12])
808
+
809
+ def test_iter_assign_mapping():
810
+ a = np.arange(24, dtype='f8').reshape(2, 3, 4).T
811
+ it = np.nditer(a, [], [['readwrite', 'updateifcopy']],
812
+ casting='same_kind', op_dtypes=[np.dtype('f4')])
813
+ with it:
814
+ it.operands[0][...] = 3
815
+ it.operands[0][...] = 14
816
+ assert_equal(a, 14)
817
+ it = np.nditer(a, [], [['readwrite', 'updateifcopy']],
818
+ casting='same_kind', op_dtypes=[np.dtype('f4')])
819
+ with it:
820
+ x = it.operands[0][-1:1]
821
+ x[...] = 14
822
+ it.operands[0][...] = -1234
823
+ assert_equal(a, -1234)
824
+ # check for no warnings on dealloc
825
+ x = None
826
+ it = None
827
+
828
+ def test_iter_nbo_align_contig():
829
+ # Check that byte order, alignment, and contig changes work
830
+
831
+ # Byte order change by requesting a specific dtype
832
+ a = np.arange(6, dtype='f4')
833
+ au = a.byteswap()
834
+ au = au.view(au.dtype.newbyteorder())
835
+ assert_(a.dtype.byteorder != au.dtype.byteorder)
836
+ i = nditer(au, [], [['readwrite', 'updateifcopy']],
837
+ casting='equiv',
838
+ op_dtypes=[np.dtype('f4')])
839
+ with i:
840
+ # context manager triggers WRITEBACKIFCOPY on i at exit
841
+ assert_equal(i.dtypes[0].byteorder, a.dtype.byteorder)
842
+ assert_equal(i.operands[0].dtype.byteorder, a.dtype.byteorder)
843
+ assert_equal(i.operands[0], a)
844
+ i.operands[0][:] = 2
845
+ assert_equal(au, [2] * 6)
846
+ del i # should not raise a warning
847
+ # Byte order change by requesting NBO
848
+ a = np.arange(6, dtype='f4')
849
+ au = a.byteswap()
850
+ au = au.view(au.dtype.newbyteorder())
851
+ assert_(a.dtype.byteorder != au.dtype.byteorder)
852
+ with nditer(au, [], [['readwrite', 'updateifcopy', 'nbo']],
853
+ casting='equiv') as i:
854
+ # context manager triggers UPDATEIFCOPY on i at exit
855
+ assert_equal(i.dtypes[0].byteorder, a.dtype.byteorder)
856
+ assert_equal(i.operands[0].dtype.byteorder, a.dtype.byteorder)
857
+ assert_equal(i.operands[0], a)
858
+ i.operands[0][:] = 12345
859
+ i.operands[0][:] = 2
860
+ assert_equal(au, [2] * 6)
861
+
862
+ # Unaligned input
863
+ a = np.zeros((6 * 4 + 1,), dtype='i1')[1:]
864
+ a = a.view('f4')
865
+ a[:] = np.arange(6, dtype='f4')
866
+ assert_(not a.flags.aligned)
867
+ # Without 'aligned', shouldn't copy
868
+ i = nditer(a, [], [['readonly']])
869
+ assert_(not i.operands[0].flags.aligned)
870
+ assert_equal(i.operands[0], a)
871
+ # With 'aligned', should make a copy
872
+ with nditer(a, [], [['readwrite', 'updateifcopy', 'aligned']]) as i:
873
+ assert_(i.operands[0].flags.aligned)
874
+ # context manager triggers UPDATEIFCOPY on i at exit
875
+ assert_equal(i.operands[0], a)
876
+ i.operands[0][:] = 3
877
+ assert_equal(a, [3] * 6)
878
+
879
+ # Discontiguous input
880
+ a = arange(12)
881
+ # If it is contiguous, shouldn't copy
882
+ i = nditer(a[:6], [], [['readonly']])
883
+ assert_(i.operands[0].flags.contiguous)
884
+ assert_equal(i.operands[0], a[:6])
885
+ # If it isn't contiguous, should buffer
886
+ i = nditer(a[::2], ['buffered', 'external_loop'],
887
+ [['readonly', 'contig']],
888
+ buffersize=10)
889
+ assert_(i[0].flags.contiguous)
890
+ assert_equal(i[0], a[::2])
891
+
892
+ def test_iter_array_cast():
893
+ # Check that arrays are cast as requested
894
+
895
+ # No cast 'f4' -> 'f4'
896
+ a = np.arange(6, dtype='f4').reshape(2, 3)
897
+ i = nditer(a, [], [['readwrite']], op_dtypes=[np.dtype('f4')])
898
+ with i:
899
+ assert_equal(i.operands[0], a)
900
+ assert_equal(i.operands[0].dtype, np.dtype('f4'))
901
+
902
+ # Byte-order cast '<f4' -> '>f4'
903
+ a = np.arange(6, dtype='<f4').reshape(2, 3)
904
+ with nditer(a, [], [['readwrite', 'updateifcopy']],
905
+ casting='equiv',
906
+ op_dtypes=[np.dtype('>f4')]) as i:
907
+ assert_equal(i.operands[0], a)
908
+ assert_equal(i.operands[0].dtype, np.dtype('>f4'))
909
+
910
+ # Safe case 'f4' -> 'f8'
911
+ a = np.arange(24, dtype='f4').reshape(2, 3, 4).swapaxes(1, 2)
912
+ i = nditer(a, [], [['readonly', 'copy']],
913
+ casting='safe',
914
+ op_dtypes=[np.dtype('f8')])
915
+ assert_equal(i.operands[0], a)
916
+ assert_equal(i.operands[0].dtype, np.dtype('f8'))
917
+ # The memory layout of the temporary should match a (a is (48,4,16))
918
+ # except negative strides get flipped to positive strides.
919
+ assert_equal(i.operands[0].strides, (96, 8, 32))
920
+ a = a[::-1, :, ::-1]
921
+ i = nditer(a, [], [['readonly', 'copy']],
922
+ casting='safe',
923
+ op_dtypes=[np.dtype('f8')])
924
+ assert_equal(i.operands[0], a)
925
+ assert_equal(i.operands[0].dtype, np.dtype('f8'))
926
+ assert_equal(i.operands[0].strides, (96, 8, 32))
927
+
928
+ # Same-kind cast 'f8' -> 'f4' -> 'f8'
929
+ a = np.arange(24, dtype='f8').reshape(2, 3, 4).T
930
+ with nditer(a, [],
931
+ [['readwrite', 'updateifcopy']],
932
+ casting='same_kind',
933
+ op_dtypes=[np.dtype('f4')]) as i:
934
+ assert_equal(i.operands[0], a)
935
+ assert_equal(i.operands[0].dtype, np.dtype('f4'))
936
+ assert_equal(i.operands[0].strides, (4, 16, 48))
937
+ # Check that WRITEBACKIFCOPY is activated at exit
938
+ i.operands[0][2, 1, 1] = -12.5
939
+ assert_(a[2, 1, 1] != -12.5)
940
+ assert_equal(a[2, 1, 1], -12.5)
941
+
942
+ a = np.arange(6, dtype='i4')[::-2]
943
+ with nditer(a, [],
944
+ [['writeonly', 'updateifcopy']],
945
+ casting='unsafe',
946
+ op_dtypes=[np.dtype('f4')]) as i:
947
+ assert_equal(i.operands[0].dtype, np.dtype('f4'))
948
+ # Even though the stride was negative in 'a', it
949
+ # becomes positive in the temporary
950
+ assert_equal(i.operands[0].strides, (4,))
951
+ i.operands[0][:] = [1, 2, 3]
952
+ assert_equal(a, [1, 2, 3])
953
+
954
+ def test_iter_array_cast_errors():
955
+ # Check that invalid casts are caught
956
+
957
+ # Need to enable copying for casts to occur
958
+ assert_raises(TypeError, nditer, arange(2, dtype='f4'), [],
959
+ [['readonly']], op_dtypes=[np.dtype('f8')])
960
+ # Also need to allow casting for casts to occur
961
+ assert_raises(TypeError, nditer, arange(2, dtype='f4'), [],
962
+ [['readonly', 'copy']], casting='no',
963
+ op_dtypes=[np.dtype('f8')])
964
+ assert_raises(TypeError, nditer, arange(2, dtype='f4'), [],
965
+ [['readonly', 'copy']], casting='equiv',
966
+ op_dtypes=[np.dtype('f8')])
967
+ assert_raises(TypeError, nditer, arange(2, dtype='f8'), [],
968
+ [['writeonly', 'updateifcopy']],
969
+ casting='no',
970
+ op_dtypes=[np.dtype('f4')])
971
+ assert_raises(TypeError, nditer, arange(2, dtype='f8'), [],
972
+ [['writeonly', 'updateifcopy']],
973
+ casting='equiv',
974
+ op_dtypes=[np.dtype('f4')])
975
+ # '<f4' -> '>f4' should not work with casting='no'
976
+ assert_raises(TypeError, nditer, arange(2, dtype='<f4'), [],
977
+ [['readonly', 'copy']], casting='no',
978
+ op_dtypes=[np.dtype('>f4')])
979
+ # 'f4' -> 'f8' is a safe cast, but 'f8' -> 'f4' isn't
980
+ assert_raises(TypeError, nditer, arange(2, dtype='f4'), [],
981
+ [['readwrite', 'updateifcopy']],
982
+ casting='safe',
983
+ op_dtypes=[np.dtype('f8')])
984
+ assert_raises(TypeError, nditer, arange(2, dtype='f8'), [],
985
+ [['readwrite', 'updateifcopy']],
986
+ casting='safe',
987
+ op_dtypes=[np.dtype('f4')])
988
+ # 'f4' -> 'i4' is neither a safe nor a same-kind cast
989
+ assert_raises(TypeError, nditer, arange(2, dtype='f4'), [],
990
+ [['readonly', 'copy']],
991
+ casting='same_kind',
992
+ op_dtypes=[np.dtype('i4')])
993
+ assert_raises(TypeError, nditer, arange(2, dtype='i4'), [],
994
+ [['writeonly', 'updateifcopy']],
995
+ casting='same_kind',
996
+ op_dtypes=[np.dtype('f4')])
997
+
998
+ def test_iter_scalar_cast():
999
+ # Check that scalars are cast as requested
1000
+
1001
+ # No cast 'f4' -> 'f4'
1002
+ i = nditer(np.float32(2.5), [], [['readonly']],
1003
+ op_dtypes=[np.dtype('f4')])
1004
+ assert_equal(i.dtypes[0], np.dtype('f4'))
1005
+ assert_equal(i.value.dtype, np.dtype('f4'))
1006
+ assert_equal(i.value, 2.5)
1007
+ # Safe cast 'f4' -> 'f8'
1008
+ i = nditer(np.float32(2.5), [],
1009
+ [['readonly', 'copy']],
1010
+ casting='safe',
1011
+ op_dtypes=[np.dtype('f8')])
1012
+ assert_equal(i.dtypes[0], np.dtype('f8'))
1013
+ assert_equal(i.value.dtype, np.dtype('f8'))
1014
+ assert_equal(i.value, 2.5)
1015
+ # Same-kind cast 'f8' -> 'f4'
1016
+ i = nditer(np.float64(2.5), [],
1017
+ [['readonly', 'copy']],
1018
+ casting='same_kind',
1019
+ op_dtypes=[np.dtype('f4')])
1020
+ assert_equal(i.dtypes[0], np.dtype('f4'))
1021
+ assert_equal(i.value.dtype, np.dtype('f4'))
1022
+ assert_equal(i.value, 2.5)
1023
+ # Unsafe cast 'f8' -> 'i4'
1024
+ i = nditer(np.float64(3.0), [],
1025
+ [['readonly', 'copy']],
1026
+ casting='unsafe',
1027
+ op_dtypes=[np.dtype('i4')])
1028
+ assert_equal(i.dtypes[0], np.dtype('i4'))
1029
+ assert_equal(i.value.dtype, np.dtype('i4'))
1030
+ assert_equal(i.value, 3)
1031
+ # Readonly scalars may be cast even without setting COPY or BUFFERED
1032
+ i = nditer(3, [], [['readonly']], op_dtypes=[np.dtype('f8')])
1033
+ assert_equal(i[0].dtype, np.dtype('f8'))
1034
+ assert_equal(i[0], 3.)
1035
+
1036
+ def test_iter_scalar_cast_errors():
1037
+ # Check that invalid casts are caught
1038
+
1039
+ # Need to allow copying/buffering for write casts of scalars to occur
1040
+ assert_raises(TypeError, nditer, np.float32(2), [],
1041
+ [['readwrite']], op_dtypes=[np.dtype('f8')])
1042
+ assert_raises(TypeError, nditer, 2.5, [],
1043
+ [['readwrite']], op_dtypes=[np.dtype('f4')])
1044
+ # 'f8' -> 'f4' isn't a safe cast if the value would overflow
1045
+ assert_raises(TypeError, nditer, np.float64(1e60), [],
1046
+ [['readonly']],
1047
+ casting='safe',
1048
+ op_dtypes=[np.dtype('f4')])
1049
+ # 'f4' -> 'i4' is neither a safe nor a same-kind cast
1050
+ assert_raises(TypeError, nditer, np.float32(2), [],
1051
+ [['readonly']],
1052
+ casting='same_kind',
1053
+ op_dtypes=[np.dtype('i4')])
1054
+
1055
+ def test_iter_object_arrays_basic():
1056
+ # Check that object arrays work
1057
+
1058
+ obj = {'a': 3, 'b': 'd'}
1059
+ a = np.array([[1, 2, 3], None, obj, None], dtype='O')
1060
+ if HAS_REFCOUNT:
1061
+ rc = sys.getrefcount(obj)
1062
+
1063
+ # Need to allow references for object arrays
1064
+ assert_raises(TypeError, nditer, a)
1065
+ if HAS_REFCOUNT:
1066
+ assert_equal(sys.getrefcount(obj), rc)
1067
+
1068
+ i = nditer(a, ['refs_ok'], ['readonly'])
1069
+ vals = [x_[()] for x_ in i]
1070
+ assert_equal(np.array(vals, dtype='O'), a)
1071
+ vals, i, x = [None] * 3
1072
+ if HAS_REFCOUNT:
1073
+ assert_equal(sys.getrefcount(obj), rc)
1074
+
1075
+ i = nditer(a.reshape(2, 2).T, ['refs_ok', 'buffered'],
1076
+ ['readonly'], order='C')
1077
+ assert_(i.iterationneedsapi)
1078
+ vals = [x_[()] for x_ in i]
1079
+ assert_equal(np.array(vals, dtype='O'), a.reshape(2, 2).ravel(order='F'))
1080
+ vals, i, x = [None] * 3
1081
+ if HAS_REFCOUNT:
1082
+ assert_equal(sys.getrefcount(obj), rc)
1083
+
1084
+ i = nditer(a.reshape(2, 2).T, ['refs_ok', 'buffered'],
1085
+ ['readwrite'], order='C')
1086
+ with i:
1087
+ for x in i:
1088
+ x[...] = None
1089
+ vals, i, x = [None] * 3
1090
+ if HAS_REFCOUNT:
1091
+ assert_(sys.getrefcount(obj) == rc - 1)
1092
+ assert_equal(a, np.array([None] * 4, dtype='O'))
1093
+
1094
+ def test_iter_object_arrays_conversions():
1095
+ # Conversions to/from objects
1096
+ a = np.arange(6, dtype='O')
1097
+ i = nditer(a, ['refs_ok', 'buffered'], ['readwrite'],
1098
+ casting='unsafe', op_dtypes='i4')
1099
+ with i:
1100
+ for x in i:
1101
+ x[...] += 1
1102
+ assert_equal(a, np.arange(6) + 1)
1103
+
1104
+ a = np.arange(6, dtype='i4')
1105
+ i = nditer(a, ['refs_ok', 'buffered'], ['readwrite'],
1106
+ casting='unsafe', op_dtypes='O')
1107
+ with i:
1108
+ for x in i:
1109
+ x[...] += 1
1110
+ assert_equal(a, np.arange(6) + 1)
1111
+
1112
+ # Non-contiguous object array
1113
+ a = np.zeros((6,), dtype=[('p', 'i1'), ('a', 'O')])
1114
+ a = a['a']
1115
+ a[:] = np.arange(6)
1116
+ i = nditer(a, ['refs_ok', 'buffered'], ['readwrite'],
1117
+ casting='unsafe', op_dtypes='i4')
1118
+ with i:
1119
+ for x in i:
1120
+ x[...] += 1
1121
+ assert_equal(a, np.arange(6) + 1)
1122
+
1123
+ # Non-contiguous value array
1124
+ a = np.zeros((6,), dtype=[('p', 'i1'), ('a', 'i4')])
1125
+ a = a['a']
1126
+ a[:] = np.arange(6) + 98172488
1127
+ i = nditer(a, ['refs_ok', 'buffered'], ['readwrite'],
1128
+ casting='unsafe', op_dtypes='O')
1129
+ with i:
1130
+ ob = i[0][()]
1131
+ if HAS_REFCOUNT:
1132
+ rc = sys.getrefcount(ob)
1133
+ for x in i:
1134
+ x[...] += 1
1135
+ if HAS_REFCOUNT:
1136
+ newrc = sys.getrefcount(ob)
1137
+ assert_(newrc == rc - 1)
1138
+ assert_equal(a, np.arange(6) + 98172489)
1139
+
1140
+ def test_iter_common_dtype():
1141
+ # Check that the iterator finds a common data type correctly
1142
+ # (some checks are somewhat duplicate after adopting NEP 50)
1143
+
1144
+ i = nditer([array([3], dtype='f4'), array([0], dtype='f8')],
1145
+ ['common_dtype'],
1146
+ [['readonly', 'copy']] * 2,
1147
+ casting='safe')
1148
+ assert_equal(i.dtypes[0], np.dtype('f8'))
1149
+ assert_equal(i.dtypes[1], np.dtype('f8'))
1150
+ i = nditer([array([3], dtype='i4'), array([0], dtype='f4')],
1151
+ ['common_dtype'],
1152
+ [['readonly', 'copy']] * 2,
1153
+ casting='safe')
1154
+ assert_equal(i.dtypes[0], np.dtype('f8'))
1155
+ assert_equal(i.dtypes[1], np.dtype('f8'))
1156
+ i = nditer([array([3], dtype='f4'), array(0, dtype='f8')],
1157
+ ['common_dtype'],
1158
+ [['readonly', 'copy']] * 2,
1159
+ casting='same_kind')
1160
+ assert_equal(i.dtypes[0], np.dtype('f8'))
1161
+ assert_equal(i.dtypes[1], np.dtype('f8'))
1162
+ i = nditer([array([3], dtype='u4'), array(0, dtype='i4')],
1163
+ ['common_dtype'],
1164
+ [['readonly', 'copy']] * 2,
1165
+ casting='safe')
1166
+ assert_equal(i.dtypes[0], np.dtype('i8'))
1167
+ assert_equal(i.dtypes[1], np.dtype('i8'))
1168
+ i = nditer([array([3], dtype='u4'), array(-12, dtype='i4')],
1169
+ ['common_dtype'],
1170
+ [['readonly', 'copy']] * 2,
1171
+ casting='safe')
1172
+ assert_equal(i.dtypes[0], np.dtype('i8'))
1173
+ assert_equal(i.dtypes[1], np.dtype('i8'))
1174
+ i = nditer([array([3], dtype='u4'), array(-12, dtype='i4'),
1175
+ array([2j], dtype='c8'), array([9], dtype='f8')],
1176
+ ['common_dtype'],
1177
+ [['readonly', 'copy']] * 4,
1178
+ casting='safe')
1179
+ assert_equal(i.dtypes[0], np.dtype('c16'))
1180
+ assert_equal(i.dtypes[1], np.dtype('c16'))
1181
+ assert_equal(i.dtypes[2], np.dtype('c16'))
1182
+ assert_equal(i.dtypes[3], np.dtype('c16'))
1183
+ assert_equal(i.value, (3, -12, 2j, 9))
1184
+
1185
+ # When allocating outputs, other outputs aren't factored in
1186
+ i = nditer([array([3], dtype='i4'), None, array([2j], dtype='c16')], [],
1187
+ [['readonly', 'copy'],
1188
+ ['writeonly', 'allocate'],
1189
+ ['writeonly']],
1190
+ casting='safe')
1191
+ assert_equal(i.dtypes[0], np.dtype('i4'))
1192
+ assert_equal(i.dtypes[1], np.dtype('i4'))
1193
+ assert_equal(i.dtypes[2], np.dtype('c16'))
1194
+ # But, if common data types are requested, they are
1195
+ i = nditer([array([3], dtype='i4'), None, array([2j], dtype='c16')],
1196
+ ['common_dtype'],
1197
+ [['readonly', 'copy'],
1198
+ ['writeonly', 'allocate'],
1199
+ ['writeonly']],
1200
+ casting='safe')
1201
+ assert_equal(i.dtypes[0], np.dtype('c16'))
1202
+ assert_equal(i.dtypes[1], np.dtype('c16'))
1203
+ assert_equal(i.dtypes[2], np.dtype('c16'))
1204
+
1205
+ def test_iter_copy_if_overlap():
1206
+ # Ensure the iterator makes copies on read/write overlap, if requested
1207
+
1208
+ # Copy not needed, 1 op
1209
+ for flag in ['readonly', 'writeonly', 'readwrite']:
1210
+ a = arange(10)
1211
+ i = nditer([a], ['copy_if_overlap'], [[flag]])
1212
+ with i:
1213
+ assert_(i.operands[0] is a)
1214
+
1215
+ # Copy needed, 2 ops, read-write overlap
1216
+ x = arange(10)
1217
+ a = x[1:]
1218
+ b = x[:-1]
1219
+ with nditer([a, b], ['copy_if_overlap'], [['readonly'], ['readwrite']]) as i:
1220
+ assert_(not np.shares_memory(*i.operands))
1221
+
1222
+ # Copy not needed with elementwise, 2 ops, exactly same arrays
1223
+ x = arange(10)
1224
+ a = x
1225
+ b = x
1226
+ i = nditer([a, b], ['copy_if_overlap'], [['readonly', 'overlap_assume_elementwise'],
1227
+ ['readwrite', 'overlap_assume_elementwise']])
1228
+ with i:
1229
+ assert_(i.operands[0] is a and i.operands[1] is b)
1230
+ with nditer([a, b], ['copy_if_overlap'], [['readonly'], ['readwrite']]) as i:
1231
+ assert_(i.operands[0] is a and not np.shares_memory(i.operands[1], b))
1232
+
1233
+ # Copy not needed, 2 ops, no overlap
1234
+ x = arange(10)
1235
+ a = x[::2]
1236
+ b = x[1::2]
1237
+ i = nditer([a, b], ['copy_if_overlap'], [['readonly'], ['writeonly']])
1238
+ assert_(i.operands[0] is a and i.operands[1] is b)
1239
+
1240
+ # Copy needed, 2 ops, read-write overlap
1241
+ x = arange(4, dtype=np.int8)
1242
+ a = x[3:]
1243
+ b = x.view(np.int32)[:1]
1244
+ with nditer([a, b], ['copy_if_overlap'], [['readonly'], ['writeonly']]) as i:
1245
+ assert_(not np.shares_memory(*i.operands))
1246
+
1247
+ # Copy needed, 3 ops, read-write overlap
1248
+ for flag in ['writeonly', 'readwrite']:
1249
+ x = np.ones([10, 10])
1250
+ a = x
1251
+ b = x.T
1252
+ c = x
1253
+ with nditer([a, b, c], ['copy_if_overlap'],
1254
+ [['readonly'], ['readonly'], [flag]]) as i:
1255
+ a2, b2, c2 = i.operands
1256
+ assert_(not np.shares_memory(a2, c2))
1257
+ assert_(not np.shares_memory(b2, c2))
1258
+
1259
+ # Copy not needed, 3 ops, read-only overlap
1260
+ x = np.ones([10, 10])
1261
+ a = x
1262
+ b = x.T
1263
+ c = x
1264
+ i = nditer([a, b, c], ['copy_if_overlap'],
1265
+ [['readonly'], ['readonly'], ['readonly']])
1266
+ a2, b2, c2 = i.operands
1267
+ assert_(a is a2)
1268
+ assert_(b is b2)
1269
+ assert_(c is c2)
1270
+
1271
+ # Copy not needed, 3 ops, read-only overlap
1272
+ x = np.ones([10, 10])
1273
+ a = x
1274
+ b = np.ones([10, 10])
1275
+ c = x.T
1276
+ i = nditer([a, b, c], ['copy_if_overlap'],
1277
+ [['readonly'], ['writeonly'], ['readonly']])
1278
+ a2, b2, c2 = i.operands
1279
+ assert_(a is a2)
1280
+ assert_(b is b2)
1281
+ assert_(c is c2)
1282
+
1283
+ # Copy not needed, 3 ops, write-only overlap
1284
+ x = np.arange(7)
1285
+ a = x[:3]
1286
+ b = x[3:6]
1287
+ c = x[4:7]
1288
+ i = nditer([a, b, c], ['copy_if_overlap'],
1289
+ [['readonly'], ['writeonly'], ['writeonly']])
1290
+ a2, b2, c2 = i.operands
1291
+ assert_(a is a2)
1292
+ assert_(b is b2)
1293
+ assert_(c is c2)
1294
+
1295
+ def test_iter_op_axes():
1296
+ # Check that custom axes work
1297
+
1298
+ # Reverse the axes
1299
+ a = arange(6).reshape(2, 3)
1300
+ i = nditer([a, a.T], [], [['readonly']] * 2, op_axes=[[0, 1], [1, 0]])
1301
+ assert_(all([x == y for (x, y) in i]))
1302
+ a = arange(24).reshape(2, 3, 4)
1303
+ i = nditer([a.T, a], [], [['readonly']] * 2, op_axes=[[2, 1, 0], None])
1304
+ assert_(all([x == y for (x, y) in i]))
1305
+
1306
+ # Broadcast 1D to any dimension
1307
+ a = arange(1, 31).reshape(2, 3, 5)
1308
+ b = arange(1, 3)
1309
+ i = nditer([a, b], [], [['readonly']] * 2, op_axes=[None, [0, -1, -1]])
1310
+ assert_equal([x * y for (x, y) in i], (a * b.reshape(2, 1, 1)).ravel())
1311
+ b = arange(1, 4)
1312
+ i = nditer([a, b], [], [['readonly']] * 2, op_axes=[None, [-1, 0, -1]])
1313
+ assert_equal([x * y for (x, y) in i], (a * b.reshape(1, 3, 1)).ravel())
1314
+ b = arange(1, 6)
1315
+ i = nditer([a, b], [], [['readonly']] * 2,
1316
+ op_axes=[None, [np.newaxis, np.newaxis, 0]])
1317
+ assert_equal([x * y for (x, y) in i], (a * b.reshape(1, 1, 5)).ravel())
1318
+
1319
+ # Inner product-style broadcasting
1320
+ a = arange(24).reshape(2, 3, 4)
1321
+ b = arange(40).reshape(5, 2, 4)
1322
+ i = nditer([a, b], ['multi_index'], [['readonly']] * 2,
1323
+ op_axes=[[0, 1, -1, -1], [-1, -1, 0, 1]])
1324
+ assert_equal(i.shape, (2, 3, 5, 2))
1325
+
1326
+ # Matrix product-style broadcasting
1327
+ a = arange(12).reshape(3, 4)
1328
+ b = arange(20).reshape(4, 5)
1329
+ i = nditer([a, b], ['multi_index'], [['readonly']] * 2,
1330
+ op_axes=[[0, -1], [-1, 1]])
1331
+ assert_equal(i.shape, (3, 5))
1332
+
1333
+ def test_iter_op_axes_errors():
1334
+ # Check that custom axes throws errors for bad inputs
1335
+
1336
+ # Wrong number of items in op_axes
1337
+ a = arange(6).reshape(2, 3)
1338
+ assert_raises(ValueError, nditer, [a, a], [], [['readonly']] * 2,
1339
+ op_axes=[[0], [1], [0]])
1340
+ # Out of bounds items in op_axes
1341
+ assert_raises(ValueError, nditer, [a, a], [], [['readonly']] * 2,
1342
+ op_axes=[[2, 1], [0, 1]])
1343
+ assert_raises(ValueError, nditer, [a, a], [], [['readonly']] * 2,
1344
+ op_axes=[[0, 1], [2, -1]])
1345
+ # Duplicate items in op_axes
1346
+ assert_raises(ValueError, nditer, [a, a], [], [['readonly']] * 2,
1347
+ op_axes=[[0, 0], [0, 1]])
1348
+ assert_raises(ValueError, nditer, [a, a], [], [['readonly']] * 2,
1349
+ op_axes=[[0, 1], [1, 1]])
1350
+
1351
+ # Different sized arrays in op_axes
1352
+ assert_raises(ValueError, nditer, [a, a], [], [['readonly']] * 2,
1353
+ op_axes=[[0, 1], [0, 1, 0]])
1354
+
1355
+ # Non-broadcastable dimensions in the result
1356
+ assert_raises(ValueError, nditer, [a, a], [], [['readonly']] * 2,
1357
+ op_axes=[[0, 1], [1, 0]])
1358
+
1359
+ def test_iter_copy():
1360
+ # Check that copying the iterator works correctly
1361
+ a = arange(24).reshape(2, 3, 4)
1362
+
1363
+ # Simple iterator
1364
+ i = nditer(a)
1365
+ j = i.copy()
1366
+ assert_equal([x[()] for x in i], [x[()] for x in j])
1367
+
1368
+ i.iterindex = 3
1369
+ j = i.copy()
1370
+ assert_equal([x[()] for x in i], [x[()] for x in j])
1371
+
1372
+ # Buffered iterator
1373
+ i = nditer(a, ['buffered', 'ranged'], order='F', buffersize=3)
1374
+ j = i.copy()
1375
+ assert_equal([x[()] for x in i], [x[()] for x in j])
1376
+
1377
+ i.iterindex = 3
1378
+ j = i.copy()
1379
+ assert_equal([x[()] for x in i], [x[()] for x in j])
1380
+
1381
+ i.iterrange = (3, 9)
1382
+ j = i.copy()
1383
+ assert_equal([x[()] for x in i], [x[()] for x in j])
1384
+
1385
+ i.iterrange = (2, 18)
1386
+ next(i)
1387
+ next(i)
1388
+ j = i.copy()
1389
+ assert_equal([x[()] for x in i], [x[()] for x in j])
1390
+
1391
+ # Casting iterator
1392
+ with nditer(a, ['buffered'], order='F', casting='unsafe',
1393
+ op_dtypes='f8', buffersize=5) as i:
1394
+ j = i.copy()
1395
+ assert_equal([x[()] for x in j], a.ravel(order='F'))
1396
+
1397
+ a = arange(24, dtype='<i4').reshape(2, 3, 4)
1398
+ with nditer(a, ['buffered'], order='F', casting='unsafe',
1399
+ op_dtypes='>f8', buffersize=5) as i:
1400
+ j = i.copy()
1401
+ assert_equal([x[()] for x in j], a.ravel(order='F'))
1402
+
1403
+
1404
+ @pytest.mark.parametrize("dtype", np.typecodes["All"])
1405
+ @pytest.mark.parametrize("loop_dtype", np.typecodes["All"])
1406
+ @pytest.mark.filterwarnings("ignore::numpy.exceptions.ComplexWarning")
1407
+ def test_iter_copy_casts(dtype, loop_dtype):
1408
+ # Ensure the dtype is never flexible:
1409
+ if loop_dtype.lower() == "m":
1410
+ loop_dtype = loop_dtype + "[ms]"
1411
+ elif np.dtype(loop_dtype).itemsize == 0:
1412
+ loop_dtype = loop_dtype + "50"
1413
+
1414
+ # Make things a bit more interesting by requiring a byte-swap as well:
1415
+ arr = np.ones(1000, dtype=np.dtype(dtype).newbyteorder())
1416
+ try:
1417
+ expected = arr.astype(loop_dtype)
1418
+ except Exception:
1419
+ # Some casts are not possible, do not worry about them
1420
+ return
1421
+
1422
+ it = np.nditer((arr,), ["buffered", "external_loop", "refs_ok"],
1423
+ op_dtypes=[loop_dtype], casting="unsafe")
1424
+
1425
+ if np.issubdtype(np.dtype(loop_dtype), np.number):
1426
+ # Casting to strings may be strange, but for simple dtypes do not rely
1427
+ # on the cast being correct:
1428
+ assert_array_equal(expected, np.ones(1000, dtype=loop_dtype))
1429
+
1430
+ it_copy = it.copy()
1431
+ res = next(it)
1432
+ del it
1433
+ res_copy = next(it_copy)
1434
+ del it_copy
1435
+
1436
+ assert_array_equal(res, expected)
1437
+ assert_array_equal(res_copy, expected)
1438
+
1439
+
1440
+ def test_iter_copy_casts_structured():
1441
+ # Test a complicated structured dtype for casting, as it requires
1442
+ # both multiple steps and a more complex casting setup.
1443
+ # Includes a structured -> unstructured (any to object), and many other
1444
+ # casts, which cause this to require all steps in the casting machinery
1445
+ # one level down as well as the iterator copy (which uses NpyAuxData clone)
1446
+ in_dtype = np.dtype([("a", np.dtype("i,")),
1447
+ ("b", np.dtype(">i,<i,>d,S17,>d,3f,O,i1"))])
1448
+ out_dtype = np.dtype([("a", np.dtype("O")),
1449
+ ("b", np.dtype(">i,>i,S17,>d,>U3,3d,i1,O"))])
1450
+ arr = np.ones(1000, dtype=in_dtype)
1451
+
1452
+ it = np.nditer((arr,), ["buffered", "external_loop", "refs_ok"],
1453
+ op_dtypes=[out_dtype], casting="unsafe")
1454
+ it_copy = it.copy()
1455
+
1456
+ res1 = next(it)
1457
+ del it
1458
+ res2 = next(it_copy)
1459
+ del it_copy
1460
+
1461
+ expected = arr["a"].astype(out_dtype["a"])
1462
+ assert_array_equal(res1["a"], expected)
1463
+ assert_array_equal(res2["a"], expected)
1464
+
1465
+ for field in in_dtype["b"].names:
1466
+ # Note that the .base avoids the subarray field
1467
+ expected = arr["b"][field].astype(out_dtype["b"][field].base)
1468
+ assert_array_equal(res1["b"][field], expected)
1469
+ assert_array_equal(res2["b"][field], expected)
1470
+
1471
+
1472
+ def test_iter_copy_casts_structured2():
1473
+ # Similar to the above, this is a fairly arcane test to cover internals
1474
+ in_dtype = np.dtype([("a", np.dtype("O,O")),
1475
+ ("b", np.dtype("5O,3O,(1,)O,(1,)i,(1,)O"))])
1476
+ out_dtype = np.dtype([("a", np.dtype("O")),
1477
+ ("b", np.dtype("O,3i,4O,4O,4i"))])
1478
+
1479
+ arr = np.ones(1, dtype=in_dtype)
1480
+ it = np.nditer((arr,), ["buffered", "external_loop", "refs_ok"],
1481
+ op_dtypes=[out_dtype], casting="unsafe")
1482
+ it_copy = it.copy()
1483
+
1484
+ res1 = next(it)
1485
+ del it
1486
+ res2 = next(it_copy)
1487
+ del it_copy
1488
+
1489
+ # Array of two structured scalars:
1490
+ for res in res1, res2:
1491
+ # Cast to tuple by getitem, which may be weird and changeable?:
1492
+ assert isinstance(res["a"][0], tuple)
1493
+ assert res["a"][0] == (1, 1)
1494
+
1495
+ for res in res1, res2:
1496
+ assert_array_equal(res["b"]["f0"][0], np.ones(5, dtype=object))
1497
+ assert_array_equal(res["b"]["f1"], np.ones((1, 3), dtype="i"))
1498
+ assert res["b"]["f2"].shape == (1, 4)
1499
+ assert_array_equal(res["b"]["f2"][0], np.ones(4, dtype=object))
1500
+ assert_array_equal(res["b"]["f3"][0], np.ones(4, dtype=object))
1501
+ assert_array_equal(res["b"]["f3"][0], np.ones(4, dtype="i"))
1502
+
1503
+
1504
+ def test_iter_allocate_output_simple():
1505
+ # Check that the iterator will properly allocate outputs
1506
+
1507
+ # Simple case
1508
+ a = arange(6)
1509
+ i = nditer([a, None], [], [['readonly'], ['writeonly', 'allocate']],
1510
+ op_dtypes=[None, np.dtype('f4')])
1511
+ assert_equal(i.operands[1].shape, a.shape)
1512
+ assert_equal(i.operands[1].dtype, np.dtype('f4'))
1513
+
1514
+ def test_iter_allocate_output_buffered_readwrite():
1515
+ # Allocated output with buffering + delay_bufalloc
1516
+
1517
+ a = arange(6)
1518
+ i = nditer([a, None], ['buffered', 'delay_bufalloc'],
1519
+ [['readonly'], ['allocate', 'readwrite']])
1520
+ with i:
1521
+ i.operands[1][:] = 1
1522
+ i.reset()
1523
+ for x in i:
1524
+ x[1][...] += x[0][...]
1525
+ assert_equal(i.operands[1], a + 1)
1526
+
1527
+ def test_iter_allocate_output_itorder():
1528
+ # The allocated output should match the iteration order
1529
+
1530
+ # C-order input, best iteration order
1531
+ a = arange(6, dtype='i4').reshape(2, 3)
1532
+ i = nditer([a, None], [], [['readonly'], ['writeonly', 'allocate']],
1533
+ op_dtypes=[None, np.dtype('f4')])
1534
+ assert_equal(i.operands[1].shape, a.shape)
1535
+ assert_equal(i.operands[1].strides, a.strides)
1536
+ assert_equal(i.operands[1].dtype, np.dtype('f4'))
1537
+ # F-order input, best iteration order
1538
+ a = arange(24, dtype='i4').reshape(2, 3, 4).T
1539
+ i = nditer([a, None], [], [['readonly'], ['writeonly', 'allocate']],
1540
+ op_dtypes=[None, np.dtype('f4')])
1541
+ assert_equal(i.operands[1].shape, a.shape)
1542
+ assert_equal(i.operands[1].strides, a.strides)
1543
+ assert_equal(i.operands[1].dtype, np.dtype('f4'))
1544
+ # Non-contiguous input, C iteration order
1545
+ a = arange(24, dtype='i4').reshape(2, 3, 4).swapaxes(0, 1)
1546
+ i = nditer([a, None], [],
1547
+ [['readonly'], ['writeonly', 'allocate']],
1548
+ order='C',
1549
+ op_dtypes=[None, np.dtype('f4')])
1550
+ assert_equal(i.operands[1].shape, a.shape)
1551
+ assert_equal(i.operands[1].strides, (32, 16, 4))
1552
+ assert_equal(i.operands[1].dtype, np.dtype('f4'))
1553
+
1554
+ def test_iter_allocate_output_opaxes():
1555
+ # Specifying op_axes should work
1556
+
1557
+ a = arange(24, dtype='i4').reshape(2, 3, 4)
1558
+ i = nditer([None, a], [], [['writeonly', 'allocate'], ['readonly']],
1559
+ op_dtypes=[np.dtype('u4'), None],
1560
+ op_axes=[[1, 2, 0], None])
1561
+ assert_equal(i.operands[0].shape, (4, 2, 3))
1562
+ assert_equal(i.operands[0].strides, (4, 48, 16))
1563
+ assert_equal(i.operands[0].dtype, np.dtype('u4'))
1564
+
1565
+ def test_iter_allocate_output_types_promotion():
1566
+ # Check type promotion of automatic outputs (this was more interesting
1567
+ # before NEP 50...)
1568
+
1569
+ i = nditer([array([3], dtype='f4'), array([0], dtype='f8'), None], [],
1570
+ [['readonly']] * 2 + [['writeonly', 'allocate']])
1571
+ assert_equal(i.dtypes[2], np.dtype('f8'))
1572
+ i = nditer([array([3], dtype='i4'), array([0], dtype='f4'), None], [],
1573
+ [['readonly']] * 2 + [['writeonly', 'allocate']])
1574
+ assert_equal(i.dtypes[2], np.dtype('f8'))
1575
+ i = nditer([array([3], dtype='f4'), array(0, dtype='f8'), None], [],
1576
+ [['readonly']] * 2 + [['writeonly', 'allocate']])
1577
+ assert_equal(i.dtypes[2], np.dtype('f8'))
1578
+ i = nditer([array([3], dtype='u4'), array(0, dtype='i4'), None], [],
1579
+ [['readonly']] * 2 + [['writeonly', 'allocate']])
1580
+ assert_equal(i.dtypes[2], np.dtype('i8'))
1581
+ i = nditer([array([3], dtype='u4'), array(-12, dtype='i4'), None], [],
1582
+ [['readonly']] * 2 + [['writeonly', 'allocate']])
1583
+ assert_equal(i.dtypes[2], np.dtype('i8'))
1584
+
1585
+ def test_iter_allocate_output_types_byte_order():
1586
+ # Verify the rules for byte order changes
1587
+
1588
+ # When there's just one input, the output type exactly matches
1589
+ a = array([3], dtype='u4')
1590
+ a = a.view(a.dtype.newbyteorder())
1591
+ i = nditer([a, None], [],
1592
+ [['readonly'], ['writeonly', 'allocate']])
1593
+ assert_equal(i.dtypes[0], i.dtypes[1])
1594
+ # With two or more inputs, the output type is in native byte order
1595
+ i = nditer([a, a, None], [],
1596
+ [['readonly'], ['readonly'], ['writeonly', 'allocate']])
1597
+ assert_(i.dtypes[0] != i.dtypes[2])
1598
+ assert_equal(i.dtypes[0].newbyteorder('='), i.dtypes[2])
1599
+
1600
+ def test_iter_allocate_output_types_scalar():
1601
+ # If the inputs are all scalars, the output should be a scalar
1602
+
1603
+ i = nditer([None, 1, 2.3, np.float32(12), np.complex128(3)], [],
1604
+ [['writeonly', 'allocate']] + [['readonly']] * 4)
1605
+ assert_equal(i.operands[0].dtype, np.dtype('complex128'))
1606
+ assert_equal(i.operands[0].ndim, 0)
1607
+
1608
+ def test_iter_allocate_output_subtype():
1609
+ # Make sure that the subtype with priority wins
1610
+ class MyNDArray(np.ndarray):
1611
+ __array_priority__ = 15
1612
+
1613
+ # subclass vs ndarray
1614
+ a = np.array([[1, 2], [3, 4]]).view(MyNDArray)
1615
+ b = np.arange(4).reshape(2, 2).T
1616
+ i = nditer([a, b, None], [],
1617
+ [['readonly'], ['readonly'], ['writeonly', 'allocate']])
1618
+ assert_equal(type(a), type(i.operands[2]))
1619
+ assert_(type(b) is not type(i.operands[2]))
1620
+ assert_equal(i.operands[2].shape, (2, 2))
1621
+
1622
+ # If subtypes are disabled, we should get back an ndarray.
1623
+ i = nditer([a, b, None], [],
1624
+ [['readonly'], ['readonly'],
1625
+ ['writeonly', 'allocate', 'no_subtype']])
1626
+ assert_equal(type(b), type(i.operands[2]))
1627
+ assert_(type(a) is not type(i.operands[2]))
1628
+ assert_equal(i.operands[2].shape, (2, 2))
1629
+
1630
+ def test_iter_allocate_output_errors():
1631
+ # Check that the iterator will throw errors for bad output allocations
1632
+
1633
+ # Need an input if no output data type is specified
1634
+ a = arange(6)
1635
+ assert_raises(TypeError, nditer, [a, None], [],
1636
+ [['writeonly'], ['writeonly', 'allocate']])
1637
+ # Allocated output should be flagged for writing
1638
+ assert_raises(ValueError, nditer, [a, None], [],
1639
+ [['readonly'], ['allocate', 'readonly']])
1640
+ # Allocated output can't have buffering without delayed bufalloc
1641
+ assert_raises(ValueError, nditer, [a, None], ['buffered'],
1642
+ ['allocate', 'readwrite'])
1643
+ # Must specify dtype if there are no inputs (cannot promote existing ones;
1644
+ # maybe this should use the 'f4' here, but it does not historically.)
1645
+ assert_raises(TypeError, nditer, [None, None], [],
1646
+ [['writeonly', 'allocate'],
1647
+ ['writeonly', 'allocate']],
1648
+ op_dtypes=[None, np.dtype('f4')])
1649
+ # If using op_axes, must specify all the axes
1650
+ a = arange(24, dtype='i4').reshape(2, 3, 4)
1651
+ assert_raises(ValueError, nditer, [a, None], [],
1652
+ [['readonly'], ['writeonly', 'allocate']],
1653
+ op_dtypes=[None, np.dtype('f4')],
1654
+ op_axes=[None, [0, np.newaxis, 1]])
1655
+ # If using op_axes, the axes must be within bounds
1656
+ assert_raises(ValueError, nditer, [a, None], [],
1657
+ [['readonly'], ['writeonly', 'allocate']],
1658
+ op_dtypes=[None, np.dtype('f4')],
1659
+ op_axes=[None, [0, 3, 1]])
1660
+ # If using op_axes, there can't be duplicates
1661
+ assert_raises(ValueError, nditer, [a, None], [],
1662
+ [['readonly'], ['writeonly', 'allocate']],
1663
+ op_dtypes=[None, np.dtype('f4')],
1664
+ op_axes=[None, [0, 2, 1, 0]])
1665
+ # Not all axes may be specified if a reduction. If there is a hole
1666
+ # in op_axes, this is an error.
1667
+ a = arange(24, dtype='i4').reshape(2, 3, 4)
1668
+ assert_raises(ValueError, nditer, [a, None], ["reduce_ok"],
1669
+ [['readonly'], ['readwrite', 'allocate']],
1670
+ op_dtypes=[None, np.dtype('f4')],
1671
+ op_axes=[None, [0, np.newaxis, 2]])
1672
+
1673
+ def test_all_allocated():
1674
+ # When no output and no shape is given, `()` is used as shape.
1675
+ i = np.nditer([None], op_dtypes=["int64"])
1676
+ assert i.operands[0].shape == ()
1677
+ assert i.dtypes == (np.dtype("int64"),)
1678
+
1679
+ i = np.nditer([None], op_dtypes=["int64"], itershape=(2, 3, 4))
1680
+ assert i.operands[0].shape == (2, 3, 4)
1681
+
1682
+ def test_iter_remove_axis():
1683
+ a = arange(24).reshape(2, 3, 4)
1684
+
1685
+ i = nditer(a, ['multi_index'])
1686
+ i.remove_axis(1)
1687
+ assert_equal(list(i), a[:, 0, :].ravel())
1688
+
1689
+ a = a[::-1, :, :]
1690
+ i = nditer(a, ['multi_index'])
1691
+ i.remove_axis(0)
1692
+ assert_equal(list(i), a[0, :, :].ravel())
1693
+
1694
+ def test_iter_remove_multi_index_inner_loop():
1695
+ # Check that removing multi-index support works
1696
+
1697
+ a = arange(24).reshape(2, 3, 4)
1698
+
1699
+ i = nditer(a, ['multi_index'])
1700
+ assert_equal(i.ndim, 3)
1701
+ assert_equal(i.shape, (2, 3, 4))
1702
+ assert_equal(i.itviews[0].shape, (2, 3, 4))
1703
+
1704
+ # Removing the multi-index tracking causes all dimensions to coalesce
1705
+ before = list(i)
1706
+ i.remove_multi_index()
1707
+ after = list(i)
1708
+
1709
+ assert_equal(before, after)
1710
+ assert_equal(i.ndim, 1)
1711
+ assert_raises(ValueError, lambda i: i.shape, i)
1712
+ assert_equal(i.itviews[0].shape, (24,))
1713
+
1714
+ # Removing the inner loop means there's just one iteration
1715
+ i.reset()
1716
+ assert_equal(i.itersize, 24)
1717
+ assert_equal(i[0].shape, ())
1718
+ i.enable_external_loop()
1719
+ assert_equal(i.itersize, 24)
1720
+ assert_equal(i[0].shape, (24,))
1721
+ assert_equal(i.value, arange(24))
1722
+
1723
+ def test_iter_iterindex():
1724
+ # Make sure iterindex works
1725
+
1726
+ buffersize = 5
1727
+ a = arange(24).reshape(4, 3, 2)
1728
+ for flags in ([], ['buffered']):
1729
+ i = nditer(a, flags, buffersize=buffersize)
1730
+ assert_equal(iter_iterindices(i), list(range(24)))
1731
+ i.iterindex = 2
1732
+ assert_equal(iter_iterindices(i), list(range(2, 24)))
1733
+
1734
+ i = nditer(a, flags, order='F', buffersize=buffersize)
1735
+ assert_equal(iter_iterindices(i), list(range(24)))
1736
+ i.iterindex = 5
1737
+ assert_equal(iter_iterindices(i), list(range(5, 24)))
1738
+
1739
+ i = nditer(a[::-1], flags, order='F', buffersize=buffersize)
1740
+ assert_equal(iter_iterindices(i), list(range(24)))
1741
+ i.iterindex = 9
1742
+ assert_equal(iter_iterindices(i), list(range(9, 24)))
1743
+
1744
+ i = nditer(a[::-1, ::-1], flags, order='C', buffersize=buffersize)
1745
+ assert_equal(iter_iterindices(i), list(range(24)))
1746
+ i.iterindex = 13
1747
+ assert_equal(iter_iterindices(i), list(range(13, 24)))
1748
+
1749
+ i = nditer(a[::1, ::-1], flags, buffersize=buffersize)
1750
+ assert_equal(iter_iterindices(i), list(range(24)))
1751
+ i.iterindex = 23
1752
+ assert_equal(iter_iterindices(i), list(range(23, 24)))
1753
+ i.reset()
1754
+ i.iterindex = 2
1755
+ assert_equal(iter_iterindices(i), list(range(2, 24)))
1756
+
1757
+ def test_iter_iterrange():
1758
+ # Make sure getting and resetting the iterrange works
1759
+
1760
+ buffersize = 5
1761
+ a = arange(24, dtype='i4').reshape(4, 3, 2)
1762
+ a_fort = a.ravel(order='F')
1763
+
1764
+ i = nditer(a, ['ranged'], ['readonly'], order='F',
1765
+ buffersize=buffersize)
1766
+ assert_equal(i.iterrange, (0, 24))
1767
+ assert_equal([x[()] for x in i], a_fort)
1768
+ for r in [(0, 24), (1, 2), (3, 24), (5, 5), (0, 20), (23, 24)]:
1769
+ i.iterrange = r
1770
+ assert_equal(i.iterrange, r)
1771
+ assert_equal([x[()] for x in i], a_fort[r[0]:r[1]])
1772
+
1773
+ i = nditer(a, ['ranged', 'buffered'], ['readonly'], order='F',
1774
+ op_dtypes='f8', buffersize=buffersize)
1775
+ assert_equal(i.iterrange, (0, 24))
1776
+ assert_equal([x[()] for x in i], a_fort)
1777
+ for r in [(0, 24), (1, 2), (3, 24), (5, 5), (0, 20), (23, 24)]:
1778
+ i.iterrange = r
1779
+ assert_equal(i.iterrange, r)
1780
+ assert_equal([x[()] for x in i], a_fort[r[0]:r[1]])
1781
+
1782
+ def get_array(i):
1783
+ val = np.array([], dtype='f8')
1784
+ for x in i:
1785
+ val = np.concatenate((val, x))
1786
+ return val
1787
+
1788
+ i = nditer(a, ['ranged', 'buffered', 'external_loop'],
1789
+ ['readonly'], order='F',
1790
+ op_dtypes='f8', buffersize=buffersize)
1791
+ assert_equal(i.iterrange, (0, 24))
1792
+ assert_equal(get_array(i), a_fort)
1793
+ for r in [(0, 24), (1, 2), (3, 24), (5, 5), (0, 20), (23, 24)]:
1794
+ i.iterrange = r
1795
+ assert_equal(i.iterrange, r)
1796
+ assert_equal(get_array(i), a_fort[r[0]:r[1]])
1797
+
1798
+ def test_iter_buffering():
1799
+ # Test buffering with several buffer sizes and types
1800
+ arrays = []
1801
+ # F-order swapped array
1802
+ _tmp = np.arange(24, dtype='c16').reshape(2, 3, 4).T
1803
+ _tmp = _tmp.view(_tmp.dtype.newbyteorder()).byteswap()
1804
+ arrays.append(_tmp)
1805
+ # Contiguous 1-dimensional array
1806
+ arrays.append(np.arange(10, dtype='f4'))
1807
+ # Unaligned array
1808
+ a = np.zeros((4 * 16 + 1,), dtype='i1')[1:]
1809
+ a = a.view('i4')
1810
+ a[:] = np.arange(16, dtype='i4')
1811
+ arrays.append(a)
1812
+ # 4-D F-order array
1813
+ arrays.append(np.arange(120, dtype='i4').reshape(5, 3, 2, 4).T)
1814
+ for a in arrays:
1815
+ for buffersize in (1, 2, 3, 5, 8, 11, 16, 1024):
1816
+ vals = []
1817
+ i = nditer(a, ['buffered', 'external_loop'],
1818
+ [['readonly', 'nbo', 'aligned']],
1819
+ order='C',
1820
+ casting='equiv',
1821
+ buffersize=buffersize)
1822
+ while not i.finished:
1823
+ assert_(i[0].size <= buffersize)
1824
+ vals.append(i[0].copy())
1825
+ i.iternext()
1826
+ assert_equal(np.concatenate(vals), a.ravel(order='C'))
1827
+
1828
+ def test_iter_write_buffering():
1829
+ # Test that buffering of writes is working
1830
+
1831
+ # F-order swapped array
1832
+ a = np.arange(24).reshape(2, 3, 4).T
1833
+ a = a.view(a.dtype.newbyteorder()).byteswap()
1834
+ i = nditer(a, ['buffered'],
1835
+ [['readwrite', 'nbo', 'aligned']],
1836
+ casting='equiv',
1837
+ order='C',
1838
+ buffersize=16)
1839
+ x = 0
1840
+ with i:
1841
+ while not i.finished:
1842
+ i[0] = x
1843
+ x += 1
1844
+ i.iternext()
1845
+ assert_equal(a.ravel(order='C'), np.arange(24))
1846
+
1847
+ def test_iter_buffering_delayed_alloc():
1848
+ # Test that delaying buffer allocation works
1849
+
1850
+ a = np.arange(6)
1851
+ b = np.arange(1, dtype='f4')
1852
+ i = nditer([a, b], ['buffered', 'delay_bufalloc', 'multi_index', 'reduce_ok'],
1853
+ ['readwrite'],
1854
+ casting='unsafe',
1855
+ op_dtypes='f4')
1856
+ assert_(i.has_delayed_bufalloc)
1857
+ assert_raises(ValueError, lambda i: i.multi_index, i)
1858
+ assert_raises(ValueError, lambda i: i[0], i)
1859
+ assert_raises(ValueError, lambda i: i[0:2], i)
1860
+
1861
+ def assign_iter(i):
1862
+ i[0] = 0
1863
+ assert_raises(ValueError, assign_iter, i)
1864
+
1865
+ i.reset()
1866
+ assert_(not i.has_delayed_bufalloc)
1867
+ assert_equal(i.multi_index, (0,))
1868
+ with i:
1869
+ assert_equal(i[0], 0)
1870
+ i[1] = 1
1871
+ assert_equal(i[0:2], [0, 1])
1872
+ assert_equal([[x[0][()], x[1][()]] for x in i], list(zip(range(6), [1] * 6)))
1873
+
1874
+ def test_iter_buffered_cast_simple():
1875
+ # Test that buffering can handle a simple cast
1876
+
1877
+ a = np.arange(10, dtype='f4')
1878
+ i = nditer(a, ['buffered', 'external_loop'],
1879
+ [['readwrite', 'nbo', 'aligned']],
1880
+ casting='same_kind',
1881
+ op_dtypes=[np.dtype('f8')],
1882
+ buffersize=3)
1883
+ with i:
1884
+ for v in i:
1885
+ v[...] *= 2
1886
+
1887
+ assert_equal(a, 2 * np.arange(10, dtype='f4'))
1888
+
1889
+ def test_iter_buffered_cast_byteswapped():
1890
+ # Test that buffering can handle a cast which requires swap->cast->swap
1891
+
1892
+ a = np.arange(10, dtype='f4')
1893
+ a = a.view(a.dtype.newbyteorder()).byteswap()
1894
+ i = nditer(a, ['buffered', 'external_loop'],
1895
+ [['readwrite', 'nbo', 'aligned']],
1896
+ casting='same_kind',
1897
+ op_dtypes=[np.dtype('f8').newbyteorder()],
1898
+ buffersize=3)
1899
+ with i:
1900
+ for v in i:
1901
+ v[...] *= 2
1902
+
1903
+ assert_equal(a, 2 * np.arange(10, dtype='f4'))
1904
+
1905
+ with warnings.catch_warnings():
1906
+ warnings.simplefilter('ignore', np.exceptions.ComplexWarning)
1907
+
1908
+ a = np.arange(10, dtype='f8')
1909
+ a = a.view(a.dtype.newbyteorder()).byteswap()
1910
+ i = nditer(a, ['buffered', 'external_loop'],
1911
+ [['readwrite', 'nbo', 'aligned']],
1912
+ casting='unsafe',
1913
+ op_dtypes=[np.dtype('c8').newbyteorder()],
1914
+ buffersize=3)
1915
+ with i:
1916
+ for v in i:
1917
+ v[...] *= 2
1918
+
1919
+ assert_equal(a, 2 * np.arange(10, dtype='f8'))
1920
+
1921
+ def test_iter_buffered_cast_byteswapped_complex():
1922
+ # Test that buffering can handle a cast which requires swap->cast->copy
1923
+
1924
+ a = np.arange(10, dtype='c8')
1925
+ a = a.view(a.dtype.newbyteorder()).byteswap()
1926
+ a += 2j
1927
+ i = nditer(a, ['buffered', 'external_loop'],
1928
+ [['readwrite', 'nbo', 'aligned']],
1929
+ casting='same_kind',
1930
+ op_dtypes=[np.dtype('c16')],
1931
+ buffersize=3)
1932
+ with i:
1933
+ for v in i:
1934
+ v[...] *= 2
1935
+ assert_equal(a, 2 * np.arange(10, dtype='c8') + 4j)
1936
+
1937
+ a = np.arange(10, dtype='c8')
1938
+ a += 2j
1939
+ i = nditer(a, ['buffered', 'external_loop'],
1940
+ [['readwrite', 'nbo', 'aligned']],
1941
+ casting='same_kind',
1942
+ op_dtypes=[np.dtype('c16').newbyteorder()],
1943
+ buffersize=3)
1944
+ with i:
1945
+ for v in i:
1946
+ v[...] *= 2
1947
+ assert_equal(a, 2 * np.arange(10, dtype='c8') + 4j)
1948
+
1949
+ a = np.arange(10, dtype=np.clongdouble)
1950
+ a = a.view(a.dtype.newbyteorder()).byteswap()
1951
+ a += 2j
1952
+ i = nditer(a, ['buffered', 'external_loop'],
1953
+ [['readwrite', 'nbo', 'aligned']],
1954
+ casting='same_kind',
1955
+ op_dtypes=[np.dtype('c16')],
1956
+ buffersize=3)
1957
+ with i:
1958
+ for v in i:
1959
+ v[...] *= 2
1960
+ assert_equal(a, 2 * np.arange(10, dtype=np.clongdouble) + 4j)
1961
+
1962
+ a = np.arange(10, dtype=np.longdouble)
1963
+ a = a.view(a.dtype.newbyteorder()).byteswap()
1964
+ i = nditer(a, ['buffered', 'external_loop'],
1965
+ [['readwrite', 'nbo', 'aligned']],
1966
+ casting='same_kind',
1967
+ op_dtypes=[np.dtype('f4')],
1968
+ buffersize=7)
1969
+ with i:
1970
+ for v in i:
1971
+ v[...] *= 2
1972
+ assert_equal(a, 2 * np.arange(10, dtype=np.longdouble))
1973
+
1974
+ def test_iter_buffered_cast_structured_type():
1975
+ # Tests buffering of structured types
1976
+
1977
+ # simple -> struct type (duplicates the value)
1978
+ sdt = [('a', 'f4'), ('b', 'i8'), ('c', 'c8', (2, 3)), ('d', 'O')]
1979
+ a = np.arange(3, dtype='f4') + 0.5
1980
+ i = nditer(a, ['buffered', 'refs_ok'], ['readonly'],
1981
+ casting='unsafe',
1982
+ op_dtypes=sdt)
1983
+ vals = [np.array(x) for x in i]
1984
+ assert_equal(vals[0]['a'], 0.5)
1985
+ assert_equal(vals[0]['b'], 0)
1986
+ assert_equal(vals[0]['c'], [[(0.5)] * 3] * 2)
1987
+ assert_equal(vals[0]['d'], 0.5)
1988
+ assert_equal(vals[1]['a'], 1.5)
1989
+ assert_equal(vals[1]['b'], 1)
1990
+ assert_equal(vals[1]['c'], [[(1.5)] * 3] * 2)
1991
+ assert_equal(vals[1]['d'], 1.5)
1992
+ assert_equal(vals[0].dtype, np.dtype(sdt))
1993
+
1994
+ # object -> struct type
1995
+ sdt = [('a', 'f4'), ('b', 'i8'), ('c', 'c8', (2, 3)), ('d', 'O')]
1996
+ a = np.zeros((3,), dtype='O')
1997
+ a[0] = (0.5, 0.5, [[0.5, 0.5, 0.5], [0.5, 0.5, 0.5]], 0.5)
1998
+ a[1] = (1.5, 1.5, [[1.5, 1.5, 1.5], [1.5, 1.5, 1.5]], 1.5)
1999
+ a[2] = (2.5, 2.5, [[2.5, 2.5, 2.5], [2.5, 2.5, 2.5]], 2.5)
2000
+ if HAS_REFCOUNT:
2001
+ rc = sys.getrefcount(a[0])
2002
+ i = nditer(a, ['buffered', 'refs_ok'], ['readonly'],
2003
+ casting='unsafe',
2004
+ op_dtypes=sdt)
2005
+ vals = [x.copy() for x in i]
2006
+ assert_equal(vals[0]['a'], 0.5)
2007
+ assert_equal(vals[0]['b'], 0)
2008
+ assert_equal(vals[0]['c'], [[(0.5)] * 3] * 2)
2009
+ assert_equal(vals[0]['d'], 0.5)
2010
+ assert_equal(vals[1]['a'], 1.5)
2011
+ assert_equal(vals[1]['b'], 1)
2012
+ assert_equal(vals[1]['c'], [[(1.5)] * 3] * 2)
2013
+ assert_equal(vals[1]['d'], 1.5)
2014
+ assert_equal(vals[0].dtype, np.dtype(sdt))
2015
+ vals, i, x = [None] * 3
2016
+ if HAS_REFCOUNT:
2017
+ assert_equal(sys.getrefcount(a[0]), rc)
2018
+
2019
+ # single-field struct type -> simple
2020
+ sdt = [('a', 'f4')]
2021
+ a = np.array([(5.5,), (8,)], dtype=sdt)
2022
+ i = nditer(a, ['buffered', 'refs_ok'], ['readonly'],
2023
+ casting='unsafe',
2024
+ op_dtypes='i4')
2025
+ assert_equal([x_[()] for x_ in i], [5, 8])
2026
+
2027
+ # make sure multi-field struct type -> simple doesn't work
2028
+ sdt = [('a', 'f4'), ('b', 'i8'), ('d', 'O')]
2029
+ a = np.array([(5.5, 7, 'test'), (8, 10, 11)], dtype=sdt)
2030
+ assert_raises(TypeError, lambda: (
2031
+ nditer(a, ['buffered', 'refs_ok'], ['readonly'],
2032
+ casting='unsafe',
2033
+ op_dtypes='i4')))
2034
+
2035
+ # struct type -> struct type (field-wise copy)
2036
+ sdt1 = [('a', 'f4'), ('b', 'i8'), ('d', 'O')]
2037
+ sdt2 = [('d', 'u2'), ('a', 'O'), ('b', 'f8')]
2038
+ a = np.array([(1, 2, 3), (4, 5, 6)], dtype=sdt1)
2039
+ i = nditer(a, ['buffered', 'refs_ok'], ['readonly'],
2040
+ casting='unsafe',
2041
+ op_dtypes=sdt2)
2042
+ assert_equal(i[0].dtype, np.dtype(sdt2))
2043
+ assert_equal([np.array(x_) for x_ in i],
2044
+ [np.array((1, 2, 3), dtype=sdt2),
2045
+ np.array((4, 5, 6), dtype=sdt2)])
2046
+
2047
+
2048
+ def test_iter_buffered_cast_structured_type_failure_with_cleanup():
2049
+ # make sure struct type -> struct type with different
2050
+ # number of fields fails
2051
+ sdt1 = [('a', 'f4'), ('b', 'i8'), ('d', 'O')]
2052
+ sdt2 = [('b', 'O'), ('a', 'f8')]
2053
+ a = np.array([(1, 2, 3), (4, 5, 6)], dtype=sdt1)
2054
+
2055
+ for intent in ["readwrite", "readonly", "writeonly"]:
2056
+ # This test was initially designed to test an error at a different
2057
+ # place, but will now raise earlier to to the cast not being possible:
2058
+ # `assert np.can_cast(a.dtype, sdt2, casting="unsafe")` fails.
2059
+ # Without a faulty DType, there is probably no reliable
2060
+ # way to get the initial tested behaviour.
2061
+ simple_arr = np.array([1, 2], dtype="i,i") # requires clean up
2062
+ with pytest.raises(TypeError):
2063
+ nditer((simple_arr, a), ['buffered', 'refs_ok'], [intent, intent],
2064
+ casting='unsafe', op_dtypes=["f,f", sdt2])
2065
+
2066
+
2067
+ def test_buffered_cast_error_paths():
2068
+ with pytest.raises(ValueError):
2069
+ # The input is cast into an `S3` buffer
2070
+ np.nditer((np.array("a", dtype="S1"),), op_dtypes=["i"],
2071
+ casting="unsafe", flags=["buffered"])
2072
+
2073
+ # The `M8[ns]` is cast into the `S3` output
2074
+ it = np.nditer((np.array(1, dtype="i"),), op_dtypes=["S1"],
2075
+ op_flags=["writeonly"], casting="unsafe", flags=["buffered"])
2076
+ with pytest.raises(ValueError):
2077
+ with it:
2078
+ buf = next(it)
2079
+ buf[...] = "a" # cannot be converted to int.
2080
+
2081
+ @pytest.mark.skipif(IS_WASM, reason="Cannot start subprocess")
2082
+ @pytest.mark.skipif(not HAS_REFCOUNT, reason="PyPy seems to not hit this.")
2083
+ def test_buffered_cast_error_paths_unraisable():
2084
+ # The following gives an unraisable error. Pytest sometimes captures that
2085
+ # (depending python and/or pytest version). So with Python>=3.8 this can
2086
+ # probably be cleaned out in the future to check for
2087
+ # pytest.PytestUnraisableExceptionWarning:
2088
+ code = textwrap.dedent("""
2089
+ import numpy as np
2090
+
2091
+ it = np.nditer((np.array(1, dtype="i"),), op_dtypes=["S1"],
2092
+ op_flags=["writeonly"], casting="unsafe", flags=["buffered"])
2093
+ buf = next(it)
2094
+ buf[...] = "a"
2095
+ del buf, it # Flushing only happens during deallocate right now.
2096
+ """)
2097
+ res = subprocess.check_output([sys.executable, "-c", code],
2098
+ stderr=subprocess.STDOUT, text=True)
2099
+ assert "ValueError" in res
2100
+
2101
+
2102
+ def test_iter_buffered_cast_subarray():
2103
+ # Tests buffering of subarrays
2104
+
2105
+ # one element -> many (copies it to all)
2106
+ sdt1 = [('a', 'f4')]
2107
+ sdt2 = [('a', 'f8', (3, 2, 2))]
2108
+ a = np.zeros((6,), dtype=sdt1)
2109
+ a['a'] = np.arange(6)
2110
+ i = nditer(a, ['buffered', 'refs_ok'], ['readonly'],
2111
+ casting='unsafe',
2112
+ op_dtypes=sdt2)
2113
+ assert_equal(i[0].dtype, np.dtype(sdt2))
2114
+ for x, count in zip(i, list(range(6))):
2115
+ assert_(np.all(x['a'] == count))
2116
+
2117
+ # one element -> many -> back (copies it to all)
2118
+ sdt1 = [('a', 'O', (1, 1))]
2119
+ sdt2 = [('a', 'O', (3, 2, 2))]
2120
+ a = np.zeros((6,), dtype=sdt1)
2121
+ a['a'][:, 0, 0] = np.arange(6)
2122
+ i = nditer(a, ['buffered', 'refs_ok'], ['readwrite'],
2123
+ casting='unsafe',
2124
+ op_dtypes=sdt2)
2125
+ with i:
2126
+ assert_equal(i[0].dtype, np.dtype(sdt2))
2127
+ count = 0
2128
+ for x in i:
2129
+ assert_(np.all(x['a'] == count))
2130
+ x['a'][0] += 2
2131
+ count += 1
2132
+ assert_equal(a['a'], np.arange(6).reshape(6, 1, 1) + 2)
2133
+
2134
+ # many -> one element -> back (copies just element 0)
2135
+ sdt1 = [('a', 'O', (3, 2, 2))]
2136
+ sdt2 = [('a', 'O', (1,))]
2137
+ a = np.zeros((6,), dtype=sdt1)
2138
+ a['a'][:, 0, 0, 0] = np.arange(6)
2139
+ i = nditer(a, ['buffered', 'refs_ok'], ['readwrite'],
2140
+ casting='unsafe',
2141
+ op_dtypes=sdt2)
2142
+ with i:
2143
+ assert_equal(i[0].dtype, np.dtype(sdt2))
2144
+ count = 0
2145
+ for x in i:
2146
+ assert_equal(x['a'], count)
2147
+ x['a'] += 2
2148
+ count += 1
2149
+ assert_equal(a['a'], np.arange(6).reshape(6, 1, 1, 1) * np.ones((1, 3, 2, 2)) + 2)
2150
+
2151
+ # many -> one element -> back (copies just element 0)
2152
+ sdt1 = [('a', 'f8', (3, 2, 2))]
2153
+ sdt2 = [('a', 'O', (1,))]
2154
+ a = np.zeros((6,), dtype=sdt1)
2155
+ a['a'][:, 0, 0, 0] = np.arange(6)
2156
+ i = nditer(a, ['buffered', 'refs_ok'], ['readonly'],
2157
+ casting='unsafe',
2158
+ op_dtypes=sdt2)
2159
+ assert_equal(i[0].dtype, np.dtype(sdt2))
2160
+ count = 0
2161
+ for x in i:
2162
+ assert_equal(x['a'], count)
2163
+ count += 1
2164
+
2165
+ # many -> one element (copies just element 0)
2166
+ sdt1 = [('a', 'O', (3, 2, 2))]
2167
+ sdt2 = [('a', 'f4', (1,))]
2168
+ a = np.zeros((6,), dtype=sdt1)
2169
+ a['a'][:, 0, 0, 0] = np.arange(6)
2170
+ i = nditer(a, ['buffered', 'refs_ok'], ['readonly'],
2171
+ casting='unsafe',
2172
+ op_dtypes=sdt2)
2173
+ assert_equal(i[0].dtype, np.dtype(sdt2))
2174
+ count = 0
2175
+ for x in i:
2176
+ assert_equal(x['a'], count)
2177
+ count += 1
2178
+
2179
+ # many -> matching shape (straightforward copy)
2180
+ sdt1 = [('a', 'O', (3, 2, 2))]
2181
+ sdt2 = [('a', 'f4', (3, 2, 2))]
2182
+ a = np.zeros((6,), dtype=sdt1)
2183
+ a['a'] = np.arange(6 * 3 * 2 * 2).reshape(6, 3, 2, 2)
2184
+ i = nditer(a, ['buffered', 'refs_ok'], ['readonly'],
2185
+ casting='unsafe',
2186
+ op_dtypes=sdt2)
2187
+ assert_equal(i[0].dtype, np.dtype(sdt2))
2188
+ count = 0
2189
+ for x in i:
2190
+ assert_equal(x['a'], a[count]['a'])
2191
+ count += 1
2192
+
2193
+ # vector -> smaller vector (truncates)
2194
+ sdt1 = [('a', 'f8', (6,))]
2195
+ sdt2 = [('a', 'f4', (2,))]
2196
+ a = np.zeros((6,), dtype=sdt1)
2197
+ a['a'] = np.arange(6 * 6).reshape(6, 6)
2198
+ i = nditer(a, ['buffered', 'refs_ok'], ['readonly'],
2199
+ casting='unsafe',
2200
+ op_dtypes=sdt2)
2201
+ assert_equal(i[0].dtype, np.dtype(sdt2))
2202
+ count = 0
2203
+ for x in i:
2204
+ assert_equal(x['a'], a[count]['a'][:2])
2205
+ count += 1
2206
+
2207
+ # vector -> bigger vector (pads with zeros)
2208
+ sdt1 = [('a', 'f8', (2,))]
2209
+ sdt2 = [('a', 'f4', (6,))]
2210
+ a = np.zeros((6,), dtype=sdt1)
2211
+ a['a'] = np.arange(6 * 2).reshape(6, 2)
2212
+ i = nditer(a, ['buffered', 'refs_ok'], ['readonly'],
2213
+ casting='unsafe',
2214
+ op_dtypes=sdt2)
2215
+ assert_equal(i[0].dtype, np.dtype(sdt2))
2216
+ count = 0
2217
+ for x in i:
2218
+ assert_equal(x['a'][:2], a[count]['a'])
2219
+ assert_equal(x['a'][2:], [0, 0, 0, 0])
2220
+ count += 1
2221
+
2222
+ # vector -> matrix (broadcasts)
2223
+ sdt1 = [('a', 'f8', (2,))]
2224
+ sdt2 = [('a', 'f4', (2, 2))]
2225
+ a = np.zeros((6,), dtype=sdt1)
2226
+ a['a'] = np.arange(6 * 2).reshape(6, 2)
2227
+ i = nditer(a, ['buffered', 'refs_ok'], ['readonly'],
2228
+ casting='unsafe',
2229
+ op_dtypes=sdt2)
2230
+ assert_equal(i[0].dtype, np.dtype(sdt2))
2231
+ count = 0
2232
+ for x in i:
2233
+ assert_equal(x['a'][0], a[count]['a'])
2234
+ assert_equal(x['a'][1], a[count]['a'])
2235
+ count += 1
2236
+
2237
+ # vector -> matrix (broadcasts and zero-pads)
2238
+ sdt1 = [('a', 'f8', (2, 1))]
2239
+ sdt2 = [('a', 'f4', (3, 2))]
2240
+ a = np.zeros((6,), dtype=sdt1)
2241
+ a['a'] = np.arange(6 * 2).reshape(6, 2, 1)
2242
+ i = nditer(a, ['buffered', 'refs_ok'], ['readonly'],
2243
+ casting='unsafe',
2244
+ op_dtypes=sdt2)
2245
+ assert_equal(i[0].dtype, np.dtype(sdt2))
2246
+ count = 0
2247
+ for x in i:
2248
+ assert_equal(x['a'][:2, 0], a[count]['a'][:, 0])
2249
+ assert_equal(x['a'][:2, 1], a[count]['a'][:, 0])
2250
+ assert_equal(x['a'][2, :], [0, 0])
2251
+ count += 1
2252
+
2253
+ # matrix -> matrix (truncates and zero-pads)
2254
+ sdt1 = [('a', 'f8', (2, 3))]
2255
+ sdt2 = [('a', 'f4', (3, 2))]
2256
+ a = np.zeros((6,), dtype=sdt1)
2257
+ a['a'] = np.arange(6 * 2 * 3).reshape(6, 2, 3)
2258
+ i = nditer(a, ['buffered', 'refs_ok'], ['readonly'],
2259
+ casting='unsafe',
2260
+ op_dtypes=sdt2)
2261
+ assert_equal(i[0].dtype, np.dtype(sdt2))
2262
+ count = 0
2263
+ for x in i:
2264
+ assert_equal(x['a'][:2, 0], a[count]['a'][:, 0])
2265
+ assert_equal(x['a'][:2, 1], a[count]['a'][:, 1])
2266
+ assert_equal(x['a'][2, :], [0, 0])
2267
+ count += 1
2268
+
2269
+ def test_iter_buffering_badwriteback():
2270
+ # Writing back from a buffer cannot combine elements
2271
+
2272
+ # a needs write buffering, but had a broadcast dimension
2273
+ a = np.arange(6).reshape(2, 3, 1)
2274
+ b = np.arange(12).reshape(2, 3, 2)
2275
+ assert_raises(ValueError, nditer, [a, b],
2276
+ ['buffered', 'external_loop'],
2277
+ [['readwrite'], ['writeonly']],
2278
+ order='C')
2279
+
2280
+ # But if a is readonly, it's fine
2281
+ nditer([a, b], ['buffered', 'external_loop'],
2282
+ [['readonly'], ['writeonly']],
2283
+ order='C')
2284
+
2285
+ # If a has just one element, it's fine too (constant 0 stride, a reduction)
2286
+ a = np.arange(1).reshape(1, 1, 1)
2287
+ nditer([a, b], ['buffered', 'external_loop', 'reduce_ok'],
2288
+ [['readwrite'], ['writeonly']],
2289
+ order='C')
2290
+
2291
+ # check that it fails on other dimensions too
2292
+ a = np.arange(6).reshape(1, 3, 2)
2293
+ assert_raises(ValueError, nditer, [a, b],
2294
+ ['buffered', 'external_loop'],
2295
+ [['readwrite'], ['writeonly']],
2296
+ order='C')
2297
+ a = np.arange(4).reshape(2, 1, 2)
2298
+ assert_raises(ValueError, nditer, [a, b],
2299
+ ['buffered', 'external_loop'],
2300
+ [['readwrite'], ['writeonly']],
2301
+ order='C')
2302
+
2303
+ def test_iter_buffering_string():
2304
+ # Safe casting disallows shrinking strings
2305
+ a = np.array(['abc', 'a', 'abcd'], dtype=np.bytes_)
2306
+ assert_equal(a.dtype, np.dtype('S4'))
2307
+ assert_raises(TypeError, nditer, a, ['buffered'], ['readonly'],
2308
+ op_dtypes='S2')
2309
+ i = nditer(a, ['buffered'], ['readonly'], op_dtypes='S6')
2310
+ assert_equal(i[0], b'abc')
2311
+ assert_equal(i[0].dtype, np.dtype('S6'))
2312
+
2313
+ a = np.array(['abc', 'a', 'abcd'], dtype=np.str_)
2314
+ assert_equal(a.dtype, np.dtype('U4'))
2315
+ assert_raises(TypeError, nditer, a, ['buffered'], ['readonly'],
2316
+ op_dtypes='U2')
2317
+ i = nditer(a, ['buffered'], ['readonly'], op_dtypes='U6')
2318
+ assert_equal(i[0], 'abc')
2319
+ assert_equal(i[0].dtype, np.dtype('U6'))
2320
+
2321
+ def test_iter_buffering_growinner():
2322
+ # Test that the inner loop grows when no buffering is needed
2323
+ a = np.arange(30)
2324
+ i = nditer(a, ['buffered', 'growinner', 'external_loop'],
2325
+ buffersize=5)
2326
+ # Should end up with just one inner loop here
2327
+ assert_equal(i[0].size, a.size)
2328
+
2329
+
2330
+ @pytest.mark.parametrize("read_or_readwrite", ["readonly", "readwrite"])
2331
+ def test_iter_contig_flag_reduce_error(read_or_readwrite):
2332
+ # Test that a non-contiguous operand is rejected without buffering.
2333
+ # NOTE: This is true even for a reduction, where we return a 0-stride
2334
+ # below!
2335
+ with pytest.raises(TypeError, match="Iterator operand required buffering"):
2336
+ it = np.nditer(
2337
+ (np.zeros(()),), flags=["external_loop", "reduce_ok"],
2338
+ op_flags=[(read_or_readwrite, "contig"),], itershape=(10,))
2339
+
2340
+
2341
+ @pytest.mark.parametrize("arr", [
2342
+ lambda: np.zeros(()),
2343
+ lambda: np.zeros((20, 1))[::20],
2344
+ lambda: np.zeros((1, 20))[:, ::20]
2345
+ ])
2346
+ def test_iter_contig_flag_single_operand_strides(arr):
2347
+ """
2348
+ Tests the strides with the contig flag for both broadcast and non-broadcast
2349
+ operands in 3 cases where the logic is needed:
2350
+ 1. When everything has a zero stride, the broadcast op needs to repeated
2351
+ 2. When the reduce axis is the last axis (first to iterate).
2352
+ 3. When the reduce axis is the first axis (last to iterate).
2353
+
2354
+ NOTE: The semantics of the cast flag are not clearly defined when
2355
+ it comes to reduction. It is unclear that there are any users.
2356
+ """
2357
+ first_op = np.ones((10, 10))
2358
+ broadcast_op = arr()
2359
+ red_op = arr()
2360
+ # Add a first operand to ensure no axis-reordering and the result shape.
2361
+ iterator = np.nditer(
2362
+ (first_op, broadcast_op, red_op),
2363
+ flags=["external_loop", "reduce_ok", "buffered", "delay_bufalloc"],
2364
+ op_flags=[("readonly", "contig")] * 2 + [("readwrite", "contig")])
2365
+
2366
+ with iterator:
2367
+ iterator.reset()
2368
+ for f, b, r in iterator:
2369
+ # The first operand is contigouos, we should have a view
2370
+ assert np.shares_memory(f, first_op)
2371
+ # Although broadcast, the second op always has a contiguous stride
2372
+ assert b.strides[0] == 8
2373
+ assert not np.shares_memory(b, broadcast_op)
2374
+ # The reduction has a contiguous stride or a 0 stride
2375
+ if red_op.ndim == 0 or red_op.shape[-1] == 1:
2376
+ assert r.strides[0] == 0
2377
+ else:
2378
+ # The stride is 8, although it was not originally:
2379
+ assert r.strides[0] == 8
2380
+ # If the reduce stride is 0, buffering makes no difference, but we
2381
+ # do it anyway right now:
2382
+ assert not np.shares_memory(r, red_op)
2383
+
2384
+
2385
+ @pytest.mark.xfail(reason="The contig flag was always buggy.")
2386
+ def test_iter_contig_flag_incorrect():
2387
+ # This case does the wrong thing...
2388
+ iterator = np.nditer(
2389
+ (np.ones((10, 10)).T, np.ones((1, 10))),
2390
+ flags=["external_loop", "reduce_ok", "buffered", "delay_bufalloc"],
2391
+ op_flags=[("readonly", "contig")] * 2)
2392
+
2393
+ with iterator:
2394
+ iterator.reset()
2395
+ for a, b in iterator:
2396
+ # Remove a and b from locals (pytest may want to format them)
2397
+ a, b = a.strides, b.strides
2398
+ assert a == 8
2399
+ assert b == 8 # should be 8 but is 0 due to axis reorder
2400
+
2401
+
2402
+ @pytest.mark.slow
2403
+ def test_iter_buffered_reduce_reuse():
2404
+ # large enough array for all views, including negative strides.
2405
+ a = np.arange(2 * 3**5)[3**5:3**5 + 1]
2406
+ flags = ['buffered', 'delay_bufalloc', 'multi_index', 'reduce_ok', 'refs_ok']
2407
+ op_flags = [('readonly',), ('readwrite', 'allocate')]
2408
+ op_axes_list = [[(0, 1, 2), (0, 1, -1)], [(0, 1, 2), (0, -1, -1)]]
2409
+ # wrong dtype to force buffering
2410
+ op_dtypes = [float, a.dtype]
2411
+
2412
+ def get_params():
2413
+ for xs in range(-3**2, 3**2 + 1):
2414
+ for ys in range(xs, 3**2 + 1):
2415
+ for op_axes in op_axes_list:
2416
+ # last stride is reduced and because of that not
2417
+ # important for this test, as it is the inner stride.
2418
+ strides = (xs * a.itemsize, ys * a.itemsize, a.itemsize)
2419
+ arr = np.lib.stride_tricks.as_strided(a, (3, 3, 3), strides)
2420
+
2421
+ for skip in [0, 1]:
2422
+ yield arr, op_axes, skip
2423
+
2424
+ for arr, op_axes, skip in get_params():
2425
+ nditer2 = np.nditer([arr.copy(), None],
2426
+ op_axes=op_axes, flags=flags, op_flags=op_flags,
2427
+ op_dtypes=op_dtypes)
2428
+ with nditer2:
2429
+ nditer2.operands[-1][...] = 0
2430
+ nditer2.reset()
2431
+ nditer2.iterindex = skip
2432
+
2433
+ for (a2_in, b2_in) in nditer2:
2434
+ b2_in += a2_in.astype(np.int_)
2435
+
2436
+ comp_res = nditer2.operands[-1]
2437
+
2438
+ for bufsize in range(3**3):
2439
+ nditer1 = np.nditer([arr, None],
2440
+ op_axes=op_axes, flags=flags, op_flags=op_flags,
2441
+ buffersize=bufsize, op_dtypes=op_dtypes)
2442
+ with nditer1:
2443
+ nditer1.operands[-1][...] = 0
2444
+ nditer1.reset()
2445
+ nditer1.iterindex = skip
2446
+
2447
+ for (a1_in, b1_in) in nditer1:
2448
+ b1_in += a1_in.astype(np.int_)
2449
+
2450
+ res = nditer1.operands[-1]
2451
+ assert_array_equal(res, comp_res)
2452
+
2453
+
2454
+ def test_iter_buffered_reduce_reuse_core():
2455
+ # NumPy re-uses buffers for broadcast operands (as of writing when reading).
2456
+ # Test this even if the offset is manually set at some point during
2457
+ # the iteration. (not a particularly tricky path)
2458
+ arr = np.empty((1, 6, 4, 1)).reshape(1, 6, 4, 1)[:, ::3, ::2, :]
2459
+ arr[...] = np.arange(arr.size).reshape(arr.shape)
2460
+ # First and last dimension are broadcast dimensions.
2461
+ arr = np.broadcast_to(arr, (100, 2, 2, 2))
2462
+
2463
+ flags = ['buffered', 'reduce_ok', 'refs_ok', 'multi_index']
2464
+ op_flags = [('readonly',)]
2465
+
2466
+ buffersize = 100 # small enough to not fit the whole array
2467
+ it = np.nditer(arr, flags=flags, op_flags=op_flags, buffersize=100)
2468
+
2469
+ # Iterate a bit (this will cause buffering internally)
2470
+ expected = [next(it) for i in range(11)]
2471
+ # Now, manually advance to inside the core (the +1)
2472
+ it.iterindex = 10 * (2 * 2 * 2) + 1
2473
+ result = [next(it) for i in range(10)]
2474
+
2475
+ assert expected[1:] == result
2476
+
2477
+
2478
+ def test_iter_no_broadcast():
2479
+ # Test that the no_broadcast flag works
2480
+ a = np.arange(24).reshape(2, 3, 4)
2481
+ b = np.arange(6).reshape(2, 3, 1)
2482
+ c = np.arange(12).reshape(3, 4)
2483
+
2484
+ nditer([a, b, c], [],
2485
+ [['readonly', 'no_broadcast'],
2486
+ ['readonly'], ['readonly']])
2487
+ assert_raises(ValueError, nditer, [a, b, c], [],
2488
+ [['readonly'], ['readonly', 'no_broadcast'], ['readonly']])
2489
+ assert_raises(ValueError, nditer, [a, b, c], [],
2490
+ [['readonly'], ['readonly'], ['readonly', 'no_broadcast']])
2491
+
2492
+
2493
+ class TestIterNested:
2494
+
2495
+ def test_basic(self):
2496
+ # Test nested iteration basic usage
2497
+ a = arange(12).reshape(2, 3, 2)
2498
+
2499
+ i, j = np.nested_iters(a, [[0], [1, 2]])
2500
+ vals = [list(j) for _ in i]
2501
+ assert_equal(vals, [[0, 1, 2, 3, 4, 5], [6, 7, 8, 9, 10, 11]])
2502
+
2503
+ i, j = np.nested_iters(a, [[0, 1], [2]])
2504
+ vals = [list(j) for _ in i]
2505
+ assert_equal(vals, [[0, 1], [2, 3], [4, 5], [6, 7], [8, 9], [10, 11]])
2506
+
2507
+ i, j = np.nested_iters(a, [[0, 2], [1]])
2508
+ vals = [list(j) for _ in i]
2509
+ assert_equal(vals, [[0, 2, 4], [1, 3, 5], [6, 8, 10], [7, 9, 11]])
2510
+
2511
+ def test_reorder(self):
2512
+ # Test nested iteration basic usage
2513
+ a = arange(12).reshape(2, 3, 2)
2514
+
2515
+ # In 'K' order (default), it gets reordered
2516
+ i, j = np.nested_iters(a, [[0], [2, 1]])
2517
+ vals = [list(j) for _ in i]
2518
+ assert_equal(vals, [[0, 1, 2, 3, 4, 5], [6, 7, 8, 9, 10, 11]])
2519
+
2520
+ i, j = np.nested_iters(a, [[1, 0], [2]])
2521
+ vals = [list(j) for _ in i]
2522
+ assert_equal(vals, [[0, 1], [2, 3], [4, 5], [6, 7], [8, 9], [10, 11]])
2523
+
2524
+ i, j = np.nested_iters(a, [[2, 0], [1]])
2525
+ vals = [list(j) for _ in i]
2526
+ assert_equal(vals, [[0, 2, 4], [1, 3, 5], [6, 8, 10], [7, 9, 11]])
2527
+
2528
+ # In 'C' order, it doesn't
2529
+ i, j = np.nested_iters(a, [[0], [2, 1]], order='C')
2530
+ vals = [list(j) for _ in i]
2531
+ assert_equal(vals, [[0, 2, 4, 1, 3, 5], [6, 8, 10, 7, 9, 11]])
2532
+
2533
+ i, j = np.nested_iters(a, [[1, 0], [2]], order='C')
2534
+ vals = [list(j) for _ in i]
2535
+ assert_equal(vals, [[0, 1], [6, 7], [2, 3], [8, 9], [4, 5], [10, 11]])
2536
+
2537
+ i, j = np.nested_iters(a, [[2, 0], [1]], order='C')
2538
+ vals = [list(j) for _ in i]
2539
+ assert_equal(vals, [[0, 2, 4], [6, 8, 10], [1, 3, 5], [7, 9, 11]])
2540
+
2541
+ def test_flip_axes(self):
2542
+ # Test nested iteration with negative axes
2543
+ a = arange(12).reshape(2, 3, 2)[::-1, ::-1, ::-1]
2544
+
2545
+ # In 'K' order (default), the axes all get flipped
2546
+ i, j = np.nested_iters(a, [[0], [1, 2]])
2547
+ vals = [list(j) for _ in i]
2548
+ assert_equal(vals, [[0, 1, 2, 3, 4, 5], [6, 7, 8, 9, 10, 11]])
2549
+
2550
+ i, j = np.nested_iters(a, [[0, 1], [2]])
2551
+ vals = [list(j) for _ in i]
2552
+ assert_equal(vals, [[0, 1], [2, 3], [4, 5], [6, 7], [8, 9], [10, 11]])
2553
+
2554
+ i, j = np.nested_iters(a, [[0, 2], [1]])
2555
+ vals = [list(j) for _ in i]
2556
+ assert_equal(vals, [[0, 2, 4], [1, 3, 5], [6, 8, 10], [7, 9, 11]])
2557
+
2558
+ # In 'C' order, flipping axes is disabled
2559
+ i, j = np.nested_iters(a, [[0], [1, 2]], order='C')
2560
+ vals = [list(j) for _ in i]
2561
+ assert_equal(vals, [[11, 10, 9, 8, 7, 6], [5, 4, 3, 2, 1, 0]])
2562
+
2563
+ i, j = np.nested_iters(a, [[0, 1], [2]], order='C')
2564
+ vals = [list(j) for _ in i]
2565
+ assert_equal(vals, [[11, 10], [9, 8], [7, 6], [5, 4], [3, 2], [1, 0]])
2566
+
2567
+ i, j = np.nested_iters(a, [[0, 2], [1]], order='C')
2568
+ vals = [list(j) for _ in i]
2569
+ assert_equal(vals, [[11, 9, 7], [10, 8, 6], [5, 3, 1], [4, 2, 0]])
2570
+
2571
+ def test_broadcast(self):
2572
+ # Test nested iteration with broadcasting
2573
+ a = arange(2).reshape(2, 1)
2574
+ b = arange(3).reshape(1, 3)
2575
+
2576
+ i, j = np.nested_iters([a, b], [[0], [1]])
2577
+ vals = [list(j) for _ in i]
2578
+ assert_equal(vals, [[[0, 0], [0, 1], [0, 2]], [[1, 0], [1, 1], [1, 2]]])
2579
+
2580
+ i, j = np.nested_iters([a, b], [[1], [0]])
2581
+ vals = [list(j) for _ in i]
2582
+ assert_equal(vals, [[[0, 0], [1, 0]], [[0, 1], [1, 1]], [[0, 2], [1, 2]]])
2583
+
2584
+ def test_dtype_copy(self):
2585
+ # Test nested iteration with a copy to change dtype
2586
+
2587
+ # copy
2588
+ a = arange(6, dtype='i4').reshape(2, 3)
2589
+ i, j = np.nested_iters(a, [[0], [1]],
2590
+ op_flags=['readonly', 'copy'],
2591
+ op_dtypes='f8')
2592
+ assert_equal(j[0].dtype, np.dtype('f8'))
2593
+ vals = [list(j) for _ in i]
2594
+ assert_equal(vals, [[0, 1, 2], [3, 4, 5]])
2595
+ vals = None
2596
+
2597
+ # writebackifcopy - using context manager
2598
+ a = arange(6, dtype='f4').reshape(2, 3)
2599
+ i, j = np.nested_iters(a, [[0], [1]],
2600
+ op_flags=['readwrite', 'updateifcopy'],
2601
+ casting='same_kind',
2602
+ op_dtypes='f8')
2603
+ with i, j:
2604
+ assert_equal(j[0].dtype, np.dtype('f8'))
2605
+ for x in i:
2606
+ for y in j:
2607
+ y[...] += 1
2608
+ assert_equal(a, [[0, 1, 2], [3, 4, 5]])
2609
+ assert_equal(a, [[1, 2, 3], [4, 5, 6]])
2610
+
2611
+ # writebackifcopy - using close()
2612
+ a = arange(6, dtype='f4').reshape(2, 3)
2613
+ i, j = np.nested_iters(a, [[0], [1]],
2614
+ op_flags=['readwrite', 'updateifcopy'],
2615
+ casting='same_kind',
2616
+ op_dtypes='f8')
2617
+ assert_equal(j[0].dtype, np.dtype('f8'))
2618
+ for x in i:
2619
+ for y in j:
2620
+ y[...] += 1
2621
+ assert_equal(a, [[0, 1, 2], [3, 4, 5]])
2622
+ i.close()
2623
+ j.close()
2624
+ assert_equal(a, [[1, 2, 3], [4, 5, 6]])
2625
+
2626
+ def test_dtype_buffered(self):
2627
+ # Test nested iteration with buffering to change dtype
2628
+
2629
+ a = arange(6, dtype='f4').reshape(2, 3)
2630
+ i, j = np.nested_iters(a, [[0], [1]],
2631
+ flags=['buffered'],
2632
+ op_flags=['readwrite'],
2633
+ casting='same_kind',
2634
+ op_dtypes='f8')
2635
+ assert_equal(j[0].dtype, np.dtype('f8'))
2636
+ for x in i:
2637
+ for y in j:
2638
+ y[...] += 1
2639
+ assert_equal(a, [[1, 2, 3], [4, 5, 6]])
2640
+
2641
+ def test_0d(self):
2642
+ a = np.arange(12).reshape(2, 3, 2)
2643
+ i, j = np.nested_iters(a, [[], [1, 0, 2]])
2644
+ vals = [list(j) for _ in i]
2645
+ assert_equal(vals, [[0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11]])
2646
+
2647
+ i, j = np.nested_iters(a, [[1, 0, 2], []])
2648
+ vals = [list(j) for _ in i]
2649
+ assert_equal(vals, [[0], [1], [2], [3], [4], [5], [6], [7], [8], [9], [10], [11]])
2650
+
2651
+ i, j, k = np.nested_iters(a, [[2, 0], [], [1]])
2652
+ vals = []
2653
+ for x in i:
2654
+ for y in j:
2655
+ vals.append(list(k))
2656
+ assert_equal(vals, [[0, 2, 4], [1, 3, 5], [6, 8, 10], [7, 9, 11]])
2657
+
2658
+ def test_iter_nested_iters_dtype_buffered(self):
2659
+ # Test nested iteration with buffering to change dtype
2660
+
2661
+ a = arange(6, dtype='f4').reshape(2, 3)
2662
+ i, j = np.nested_iters(a, [[0], [1]],
2663
+ flags=['buffered'],
2664
+ op_flags=['readwrite'],
2665
+ casting='same_kind',
2666
+ op_dtypes='f8')
2667
+ with i, j:
2668
+ assert_equal(j[0].dtype, np.dtype('f8'))
2669
+ for x in i:
2670
+ for y in j:
2671
+ y[...] += 1
2672
+ assert_equal(a, [[1, 2, 3], [4, 5, 6]])
2673
+
2674
+ def test_iter_reduction_error():
2675
+
2676
+ a = np.arange(6)
2677
+ assert_raises(ValueError, nditer, [a, None], [],
2678
+ [['readonly'], ['readwrite', 'allocate']],
2679
+ op_axes=[[0], [-1]])
2680
+
2681
+ a = np.arange(6).reshape(2, 3)
2682
+ assert_raises(ValueError, nditer, [a, None], ['external_loop'],
2683
+ [['readonly'], ['readwrite', 'allocate']],
2684
+ op_axes=[[0, 1], [-1, -1]])
2685
+
2686
+ def test_iter_reduction():
2687
+ # Test doing reductions with the iterator
2688
+
2689
+ a = np.arange(6)
2690
+ i = nditer([a, None], ['reduce_ok'],
2691
+ [['readonly'], ['readwrite', 'allocate']],
2692
+ op_axes=[[0], [-1]])
2693
+ # Need to initialize the output operand to the addition unit
2694
+ with i:
2695
+ i.operands[1][...] = 0
2696
+ # Do the reduction
2697
+ for x, y in i:
2698
+ y[...] += x
2699
+ # Since no axes were specified, should have allocated a scalar
2700
+ assert_equal(i.operands[1].ndim, 0)
2701
+ assert_equal(i.operands[1], np.sum(a))
2702
+
2703
+ a = np.arange(6).reshape(2, 3)
2704
+ i = nditer([a, None], ['reduce_ok', 'external_loop'],
2705
+ [['readonly'], ['readwrite', 'allocate']],
2706
+ op_axes=[[0, 1], [-1, -1]])
2707
+ # Need to initialize the output operand to the addition unit
2708
+ with i:
2709
+ i.operands[1][...] = 0
2710
+ # Reduction shape/strides for the output
2711
+ assert_equal(i[1].shape, (6,))
2712
+ assert_equal(i[1].strides, (0,))
2713
+ # Do the reduction
2714
+ for x, y in i:
2715
+ # Use a for loop instead of ``y[...] += x``
2716
+ # (equivalent to ``y[...] = y[...].copy() + x``),
2717
+ # because y has zero strides we use for the reduction
2718
+ for j in range(len(y)):
2719
+ y[j] += x[j]
2720
+ # Since no axes were specified, should have allocated a scalar
2721
+ assert_equal(i.operands[1].ndim, 0)
2722
+ assert_equal(i.operands[1], np.sum(a))
2723
+
2724
+ # This is a tricky reduction case for the buffering double loop
2725
+ # to handle
2726
+ a = np.ones((2, 3, 5))
2727
+ it1 = nditer([a, None], ['reduce_ok', 'external_loop'],
2728
+ [['readonly'], ['readwrite', 'allocate']],
2729
+ op_axes=[None, [0, -1, 1]])
2730
+ it2 = nditer([a, None], ['reduce_ok', 'external_loop',
2731
+ 'buffered', 'delay_bufalloc'],
2732
+ [['readonly'], ['readwrite', 'allocate']],
2733
+ op_axes=[None, [0, -1, 1]], buffersize=10)
2734
+ with it1, it2:
2735
+ it1.operands[1].fill(0)
2736
+ it2.operands[1].fill(0)
2737
+ it2.reset()
2738
+ for x in it1:
2739
+ x[1][...] += x[0]
2740
+ for x in it2:
2741
+ x[1][...] += x[0]
2742
+ assert_equal(it1.operands[1], it2.operands[1])
2743
+ assert_equal(it2.operands[1].sum(), a.size)
2744
+
2745
+ def test_iter_buffering_reduction():
2746
+ # Test doing buffered reductions with the iterator
2747
+
2748
+ a = np.arange(6)
2749
+ b = np.array(0., dtype='f8').byteswap()
2750
+ b = b.view(b.dtype.newbyteorder())
2751
+ i = nditer([a, b], ['reduce_ok', 'buffered'],
2752
+ [['readonly'], ['readwrite', 'nbo']],
2753
+ op_axes=[[0], [-1]])
2754
+ with i:
2755
+ assert_equal(i[1].dtype, np.dtype('f8'))
2756
+ assert_(i[1].dtype != b.dtype)
2757
+ # Do the reduction
2758
+ for x, y in i:
2759
+ y[...] += x
2760
+ # Since no axes were specified, should have allocated a scalar
2761
+ assert_equal(b, np.sum(a))
2762
+
2763
+ a = np.arange(6).reshape(2, 3)
2764
+ b = np.array([0, 0], dtype='f8').byteswap()
2765
+ b = b.view(b.dtype.newbyteorder())
2766
+ i = nditer([a, b], ['reduce_ok', 'external_loop', 'buffered'],
2767
+ [['readonly'], ['readwrite', 'nbo']],
2768
+ op_axes=[[0, 1], [0, -1]])
2769
+ # Reduction shape/strides for the output
2770
+ with i:
2771
+ assert_equal(i[1].shape, (3,))
2772
+ assert_equal(i[1].strides, (0,))
2773
+ # Do the reduction
2774
+ for x, y in i:
2775
+ # Use a for loop instead of ``y[...] += x``
2776
+ # (equivalent to ``y[...] = y[...].copy() + x``),
2777
+ # because y has zero strides we use for the reduction
2778
+ for j in range(len(y)):
2779
+ y[j] += x[j]
2780
+ assert_equal(b, np.sum(a, axis=1))
2781
+
2782
+ # Iterator inner double loop was wrong on this one
2783
+ p = np.arange(2) + 1
2784
+ it = np.nditer([p, None],
2785
+ ['delay_bufalloc', 'reduce_ok', 'buffered', 'external_loop'],
2786
+ [['readonly'], ['readwrite', 'allocate']],
2787
+ op_axes=[[-1, 0], [-1, -1]],
2788
+ itershape=(2, 2))
2789
+ with it:
2790
+ it.operands[1].fill(0)
2791
+ it.reset()
2792
+ assert_equal(it[0], [1, 2, 1, 2])
2793
+
2794
+ # Iterator inner loop should take argument contiguity into account
2795
+ x = np.ones((7, 13, 8), np.int8)[4:6, 1:11:6, 1:5].transpose(1, 2, 0)
2796
+ x[...] = np.arange(x.size).reshape(x.shape)
2797
+ y_base = np.arange(4 * 4, dtype=np.int8).reshape(4, 4)
2798
+ y_base_copy = y_base.copy()
2799
+ y = y_base[::2, :, None]
2800
+
2801
+ it = np.nditer([y, x],
2802
+ ['buffered', 'external_loop', 'reduce_ok'],
2803
+ [['readwrite'], ['readonly']])
2804
+ with it:
2805
+ for a, b in it:
2806
+ a.fill(2)
2807
+
2808
+ assert_equal(y_base[1::2], y_base_copy[1::2])
2809
+ assert_equal(y_base[::2], 2)
2810
+
2811
+ def test_iter_buffering_reduction_reuse_reduce_loops():
2812
+ # There was a bug triggering reuse of the reduce loop inappropriately,
2813
+ # which caused processing to happen in unnecessarily small chunks
2814
+ # and overran the buffer.
2815
+
2816
+ a = np.zeros((2, 7))
2817
+ b = np.zeros((1, 7))
2818
+ it = np.nditer([a, b], flags=['reduce_ok', 'external_loop', 'buffered'],
2819
+ op_flags=[['readonly'], ['readwrite']],
2820
+ buffersize=5)
2821
+
2822
+ with it:
2823
+ bufsizes = [x.shape[0] for x, y in it]
2824
+ assert_equal(bufsizes, [5, 2, 5, 2])
2825
+ assert_equal(sum(bufsizes), a.size)
2826
+
2827
+ def test_iter_writemasked_badinput():
2828
+ a = np.zeros((2, 3))
2829
+ b = np.zeros((3,))
2830
+ m = np.array([[True, True, False], [False, True, False]])
2831
+ m2 = np.array([True, True, False])
2832
+ m3 = np.array([0, 1, 1], dtype='u1')
2833
+ mbad1 = np.array([0, 1, 1], dtype='i1')
2834
+ mbad2 = np.array([0, 1, 1], dtype='f4')
2835
+
2836
+ # Need an 'arraymask' if any operand is 'writemasked'
2837
+ assert_raises(ValueError, nditer, [a, m], [],
2838
+ [['readwrite', 'writemasked'], ['readonly']])
2839
+
2840
+ # A 'writemasked' operand must not be readonly
2841
+ assert_raises(ValueError, nditer, [a, m], [],
2842
+ [['readonly', 'writemasked'], ['readonly', 'arraymask']])
2843
+
2844
+ # 'writemasked' and 'arraymask' may not be used together
2845
+ assert_raises(ValueError, nditer, [a, m], [],
2846
+ [['readonly'], ['readwrite', 'arraymask', 'writemasked']])
2847
+
2848
+ # 'arraymask' may only be specified once
2849
+ assert_raises(ValueError, nditer, [a, m, m2], [],
2850
+ [['readwrite', 'writemasked'],
2851
+ ['readonly', 'arraymask'],
2852
+ ['readonly', 'arraymask']])
2853
+
2854
+ # An 'arraymask' with nothing 'writemasked' also doesn't make sense
2855
+ assert_raises(ValueError, nditer, [a, m], [],
2856
+ [['readwrite'], ['readonly', 'arraymask']])
2857
+
2858
+ # A writemasked reduction requires a similarly smaller mask
2859
+ assert_raises(ValueError, nditer, [a, b, m], ['reduce_ok'],
2860
+ [['readonly'],
2861
+ ['readwrite', 'writemasked'],
2862
+ ['readonly', 'arraymask']])
2863
+ # But this should work with a smaller/equal mask to the reduction operand
2864
+ np.nditer([a, b, m2], ['reduce_ok'],
2865
+ [['readonly'],
2866
+ ['readwrite', 'writemasked'],
2867
+ ['readonly', 'arraymask']])
2868
+ # The arraymask itself cannot be a reduction
2869
+ assert_raises(ValueError, nditer, [a, b, m2], ['reduce_ok'],
2870
+ [['readonly'],
2871
+ ['readwrite', 'writemasked'],
2872
+ ['readwrite', 'arraymask']])
2873
+
2874
+ # A uint8 mask is ok too
2875
+ np.nditer([a, m3], ['buffered'],
2876
+ [['readwrite', 'writemasked'],
2877
+ ['readonly', 'arraymask']],
2878
+ op_dtypes=['f4', None],
2879
+ casting='same_kind')
2880
+ # An int8 mask isn't ok
2881
+ assert_raises(TypeError, np.nditer, [a, mbad1], ['buffered'],
2882
+ [['readwrite', 'writemasked'],
2883
+ ['readonly', 'arraymask']],
2884
+ op_dtypes=['f4', None],
2885
+ casting='same_kind')
2886
+ # A float32 mask isn't ok
2887
+ assert_raises(TypeError, np.nditer, [a, mbad2], ['buffered'],
2888
+ [['readwrite', 'writemasked'],
2889
+ ['readonly', 'arraymask']],
2890
+ op_dtypes=['f4', None],
2891
+ casting='same_kind')
2892
+
2893
+
2894
+ def _is_buffered(iterator):
2895
+ try:
2896
+ iterator.itviews
2897
+ except ValueError:
2898
+ return True
2899
+ return False
2900
+
2901
+ @pytest.mark.parametrize("arrs",
2902
+ [np.zeros((3,), dtype='f8'),
2903
+ np.zeros((9876, 3 * 5), dtype='f8')[::2, :],
2904
+ np.zeros((4, 312, 124, 3), dtype='f8')[::2, :, ::2, :],
2905
+ # Also test with the last dimension strided (so it does not fit if
2906
+ # there is repeated access)
2907
+ np.zeros((9,), dtype='f8')[::3],
2908
+ np.zeros((9876, 3 * 10), dtype='f8')[::2, ::5],
2909
+ np.zeros((4, 312, 124, 3), dtype='f8')[::2, :, ::2, ::-1]])
2910
+ def test_iter_writemasked(arrs):
2911
+ # Note, the slicing above is to ensure that nditer cannot combine multiple
2912
+ # axes into one. The repetition is just to make things a bit more
2913
+ # interesting.
2914
+ a = arrs.copy()
2915
+ shape = a.shape
2916
+ reps = shape[-1] // 3
2917
+ msk = np.empty(shape, dtype=bool)
2918
+ msk[...] = [True, True, False] * reps
2919
+
2920
+ # When buffering is unused, 'writemasked' effectively does nothing.
2921
+ # It's up to the user of the iterator to obey the requested semantics.
2922
+ it = np.nditer([a, msk], [],
2923
+ [['readwrite', 'writemasked'],
2924
+ ['readonly', 'arraymask']])
2925
+ with it:
2926
+ for x, m in it:
2927
+ x[...] = 1
2928
+ # Because we violated the semantics, all the values became 1
2929
+ assert_equal(a, np.broadcast_to([1, 1, 1] * reps, shape))
2930
+
2931
+ # Even if buffering is enabled, we still may be accessing the array
2932
+ # directly.
2933
+ it = np.nditer([a, msk], ['buffered'],
2934
+ [['readwrite', 'writemasked'],
2935
+ ['readonly', 'arraymask']])
2936
+ # @seberg: I honestly don't currently understand why a "buffered" iterator
2937
+ # would end up not using a buffer for the small array here at least when
2938
+ # "writemasked" is used, that seems confusing... Check by testing for
2939
+ # actual memory overlap!
2940
+ is_buffered = True
2941
+ with it:
2942
+ for x, m in it:
2943
+ x[...] = 2.5
2944
+ if np.may_share_memory(x, a):
2945
+ is_buffered = False
2946
+
2947
+ if not is_buffered:
2948
+ # Because we violated the semantics, all the values became 2.5
2949
+ assert_equal(a, np.broadcast_to([2.5, 2.5, 2.5] * reps, shape))
2950
+ else:
2951
+ # For large sizes, the iterator may be buffered:
2952
+ assert_equal(a, np.broadcast_to([2.5, 2.5, 1] * reps, shape))
2953
+ a[...] = 2.5
2954
+
2955
+ # If buffering will definitely happening, for instance because of
2956
+ # a cast, only the items selected by the mask will be copied back from
2957
+ # the buffer.
2958
+ it = np.nditer([a, msk], ['buffered'],
2959
+ [['readwrite', 'writemasked'],
2960
+ ['readonly', 'arraymask']],
2961
+ op_dtypes=['i8', None],
2962
+ casting='unsafe')
2963
+ with it:
2964
+ for x, m in it:
2965
+ x[...] = 3
2966
+ # Even though we violated the semantics, only the selected values
2967
+ # were copied back
2968
+ assert_equal(a, np.broadcast_to([3, 3, 2.5] * reps, shape))
2969
+
2970
+
2971
+ @pytest.mark.parametrize(["mask", "mask_axes"], [
2972
+ # Allocated operand (only broadcasts with -1)
2973
+ (None, [-1, 0]),
2974
+ # Reduction along the first dimension (with and without op_axes)
2975
+ (np.zeros((1, 4), dtype="bool"), [0, 1]),
2976
+ (np.zeros((1, 4), dtype="bool"), None),
2977
+ # Test 0-D and -1 op_axes
2978
+ (np.zeros(4, dtype="bool"), [-1, 0]),
2979
+ (np.zeros((), dtype="bool"), [-1, -1]),
2980
+ (np.zeros((), dtype="bool"), None)])
2981
+ def test_iter_writemasked_broadcast_error(mask, mask_axes):
2982
+ # This assumes that a readwrite mask makes sense. This is likely not the
2983
+ # case and should simply be deprecated.
2984
+ arr = np.zeros((3, 4))
2985
+ itflags = ["reduce_ok"]
2986
+ mask_flags = ["arraymask", "readwrite", "allocate"]
2987
+ a_flags = ["writeonly", "writemasked"]
2988
+ if mask_axes is None:
2989
+ op_axes = None
2990
+ else:
2991
+ op_axes = [mask_axes, [0, 1]]
2992
+
2993
+ with assert_raises(ValueError):
2994
+ np.nditer((mask, arr), flags=itflags, op_flags=[mask_flags, a_flags],
2995
+ op_axes=op_axes)
2996
+
2997
+
2998
+ def test_iter_writemasked_decref():
2999
+ # force casting (to make it interesting) by using a structured dtype.
3000
+ arr = np.arange(10000).astype(">i,O")
3001
+ original = arr.copy()
3002
+ mask = np.random.randint(0, 2, size=10000).astype(bool)
3003
+
3004
+ it = np.nditer([arr, mask], ['buffered', "refs_ok"],
3005
+ [['readwrite', 'writemasked'],
3006
+ ['readonly', 'arraymask']],
3007
+ op_dtypes=["<i,O", "?"])
3008
+ singleton = object()
3009
+ if HAS_REFCOUNT:
3010
+ count = sys.getrefcount(singleton)
3011
+ for buf, mask_buf in it:
3012
+ buf[...] = (3, singleton)
3013
+
3014
+ del buf, mask_buf, it # delete everything to ensure correct cleanup
3015
+
3016
+ if HAS_REFCOUNT:
3017
+ # The buffer would have included additional items, they must be
3018
+ # cleared correctly:
3019
+ assert sys.getrefcount(singleton) - count == np.count_nonzero(mask)
3020
+
3021
+ assert_array_equal(arr[~mask], original[~mask])
3022
+ assert (arr[mask] == np.array((3, singleton), arr.dtype)).all()
3023
+ del arr
3024
+
3025
+ if HAS_REFCOUNT:
3026
+ assert sys.getrefcount(singleton) == count
3027
+
3028
+
3029
+ def test_iter_non_writable_attribute_deletion():
3030
+ it = np.nditer(np.ones(2))
3031
+ attr = ["value", "shape", "operands", "itviews", "has_delayed_bufalloc",
3032
+ "iterationneedsapi", "has_multi_index", "has_index", "dtypes",
3033
+ "ndim", "nop", "itersize", "finished"]
3034
+
3035
+ for s in attr:
3036
+ assert_raises(AttributeError, delattr, it, s)
3037
+
3038
+
3039
+ def test_iter_writable_attribute_deletion():
3040
+ it = np.nditer(np.ones(2))
3041
+ attr = ["multi_index", "index", "iterrange", "iterindex"]
3042
+ for s in attr:
3043
+ assert_raises(AttributeError, delattr, it, s)
3044
+
3045
+
3046
+ def test_iter_element_deletion():
3047
+ it = np.nditer(np.ones(3))
3048
+ try:
3049
+ del it[1]
3050
+ del it[1:2]
3051
+ except TypeError:
3052
+ pass
3053
+ except Exception:
3054
+ raise AssertionError
3055
+
3056
+ def test_iter_allocated_array_dtypes():
3057
+ # If the dtype of an allocated output has a shape, the shape gets
3058
+ # tacked onto the end of the result.
3059
+ it = np.nditer(([1, 3, 20], None), op_dtypes=[None, ('i4', (2,))])
3060
+ for a, b in it:
3061
+ b[0] = a - 1
3062
+ b[1] = a + 1
3063
+ assert_equal(it.operands[1], [[0, 2], [2, 4], [19, 21]])
3064
+
3065
+ # Check the same (less sensitive) thing when `op_axes` with -1 is given.
3066
+ it = np.nditer(([[1, 3, 20]], None), op_dtypes=[None, ('i4', (2,))],
3067
+ flags=["reduce_ok"], op_axes=[None, (-1, 0)])
3068
+ for a, b in it:
3069
+ b[0] = a - 1
3070
+ b[1] = a + 1
3071
+ assert_equal(it.operands[1], [[0, 2], [2, 4], [19, 21]])
3072
+
3073
+ # Make sure this works for scalars too
3074
+ it = np.nditer((10, 2, None), op_dtypes=[None, None, ('i4', (2, 2))])
3075
+ for a, b, c in it:
3076
+ c[0, 0] = a - b
3077
+ c[0, 1] = a + b
3078
+ c[1, 0] = a * b
3079
+ c[1, 1] = a / b
3080
+ assert_equal(it.operands[2], [[8, 12], [20, 5]])
3081
+
3082
+
3083
+ def test_0d_iter():
3084
+ # Basic test for iteration of 0-d arrays:
3085
+ i = nditer([2, 3], ['multi_index'], [['readonly']] * 2)
3086
+ assert_equal(i.ndim, 0)
3087
+ assert_equal(next(i), (2, 3))
3088
+ assert_equal(i.multi_index, ())
3089
+ assert_equal(i.iterindex, 0)
3090
+ assert_raises(StopIteration, next, i)
3091
+ # test reset:
3092
+ i.reset()
3093
+ assert_equal(next(i), (2, 3))
3094
+ assert_raises(StopIteration, next, i)
3095
+
3096
+ # test forcing to 0-d
3097
+ i = nditer(np.arange(5), ['multi_index'], [['readonly']], op_axes=[()])
3098
+ assert_equal(i.ndim, 0)
3099
+ assert_equal(len(i), 1)
3100
+
3101
+ i = nditer(np.arange(5), ['multi_index'], [['readonly']],
3102
+ op_axes=[()], itershape=())
3103
+ assert_equal(i.ndim, 0)
3104
+ assert_equal(len(i), 1)
3105
+
3106
+ # passing an itershape alone is not enough, the op_axes are also needed
3107
+ with assert_raises(ValueError):
3108
+ nditer(np.arange(5), ['multi_index'], [['readonly']], itershape=())
3109
+
3110
+ # Test a more complex buffered casting case (same as another test above)
3111
+ sdt = [('a', 'f4'), ('b', 'i8'), ('c', 'c8', (2, 3)), ('d', 'O')]
3112
+ a = np.array(0.5, dtype='f4')
3113
+ i = nditer(a, ['buffered', 'refs_ok'], ['readonly'],
3114
+ casting='unsafe', op_dtypes=sdt)
3115
+ vals = next(i)
3116
+ assert_equal(vals['a'], 0.5)
3117
+ assert_equal(vals['b'], 0)
3118
+ assert_equal(vals['c'], [[(0.5)] * 3] * 2)
3119
+ assert_equal(vals['d'], 0.5)
3120
+
3121
+ def test_object_iter_cleanup():
3122
+ # see gh-18450
3123
+ # object arrays can raise a python exception in ufunc inner loops using
3124
+ # nditer, which should cause iteration to stop & cleanup. There were bugs
3125
+ # in the nditer cleanup when decref'ing object arrays.
3126
+ # This test would trigger valgrind "uninitialized read" before the bugfix.
3127
+ assert_raises(TypeError, lambda: np.zeros((17000, 2), dtype='f4') * None)
3128
+
3129
+ # this more explicit code also triggers the invalid access
3130
+ arr = np.arange(ncu.BUFSIZE * 10).reshape(10, -1).astype(str)
3131
+ oarr = arr.astype(object)
3132
+ oarr[:, -1] = None
3133
+ assert_raises(TypeError, lambda: np.add(oarr[:, ::-1], arr[:, ::-1]))
3134
+
3135
+ # followup: this tests for a bug introduced in the first pass of gh-18450,
3136
+ # caused by an incorrect fallthrough of the TypeError
3137
+ class T:
3138
+ def __bool__(self):
3139
+ raise TypeError("Ambiguous")
3140
+ assert_raises(TypeError, np.logical_or.reduce,
3141
+ np.array([T(), T()], dtype='O'))
3142
+
3143
+ def test_object_iter_cleanup_reduce():
3144
+ # Similar as above, but a complex reduction case that was previously
3145
+ # missed (see gh-18810).
3146
+ # The following array is special in that it cannot be flattened:
3147
+ arr = np.array([[None, 1], [-1, -1], [None, 2], [-1, -1]])[::2]
3148
+ with pytest.raises(TypeError):
3149
+ np.sum(arr)
3150
+
3151
+ @pytest.mark.parametrize("arr", [
3152
+ np.ones((8000, 4, 2), dtype=object)[:, ::2, :],
3153
+ np.ones((8000, 4, 2), dtype=object, order="F")[:, ::2, :],
3154
+ np.ones((8000, 4, 2), dtype=object)[:, ::2, :].copy("F")])
3155
+ def test_object_iter_cleanup_large_reduce(arr):
3156
+ # More complicated calls are possible for large arrays:
3157
+ out = np.ones(8000, dtype=np.intp)
3158
+ # force casting with `dtype=object`
3159
+ res = np.sum(arr, axis=(1, 2), dtype=object, out=out)
3160
+ assert_array_equal(res, np.full(8000, 4, dtype=object))
3161
+
3162
+ def test_iter_too_large():
3163
+ # The total size of the iterator must not exceed the maximum intp due
3164
+ # to broadcasting. Dividing by 1024 will keep it small enough to
3165
+ # give a legal array.
3166
+ size = np.iinfo(np.intp).max // 1024
3167
+ arr = np.lib.stride_tricks.as_strided(np.zeros(1), (size,), (0,))
3168
+ assert_raises(ValueError, nditer, (arr, arr[:, None]))
3169
+ # test the same for multiindex. That may get more interesting when
3170
+ # removing 0 dimensional axis is allowed (since an iterator can grow then)
3171
+ assert_raises(ValueError, nditer,
3172
+ (arr, arr[:, None]), flags=['multi_index'])
3173
+
3174
+
3175
+ def test_iter_too_large_with_multiindex():
3176
+ # When a multi index is being tracked, the error is delayed this
3177
+ # checks the delayed error messages and getting below that by
3178
+ # removing an axis.
3179
+ base_size = 2**10
3180
+ num = 1
3181
+ while base_size**num < np.iinfo(np.intp).max:
3182
+ num += 1
3183
+
3184
+ shape_template = [1, 1] * num
3185
+ arrays = []
3186
+ for i in range(num):
3187
+ shape = shape_template[:]
3188
+ shape[i * 2] = 2**10
3189
+ arrays.append(np.empty(shape))
3190
+ arrays = tuple(arrays)
3191
+
3192
+ # arrays are now too large to be broadcast. The different modes test
3193
+ # different nditer functionality with or without GIL.
3194
+ for mode in range(6):
3195
+ with assert_raises(ValueError):
3196
+ _multiarray_tests.test_nditer_too_large(arrays, -1, mode)
3197
+ # but if we do nothing with the nditer, it can be constructed:
3198
+ _multiarray_tests.test_nditer_too_large(arrays, -1, 7)
3199
+
3200
+ # When an axis is removed, things should work again (half the time):
3201
+ for i in range(num):
3202
+ for mode in range(6):
3203
+ # an axis with size 1024 is removed:
3204
+ _multiarray_tests.test_nditer_too_large(arrays, i * 2, mode)
3205
+ # an axis with size 1 is removed:
3206
+ with assert_raises(ValueError):
3207
+ _multiarray_tests.test_nditer_too_large(arrays, i * 2 + 1, mode)
3208
+
3209
+
3210
+ def test_invalid_call_of_enable_external_loop():
3211
+ with pytest.raises(ValueError,
3212
+ match='Iterator flag EXTERNAL_LOOP cannot be used'):
3213
+ np.nditer(([[1], [2]], [3, 4]), ['multi_index']).enable_external_loop()
3214
+
3215
+
3216
+ def test_writebacks():
3217
+ a = np.arange(6, dtype='f4')
3218
+ au = a.byteswap()
3219
+ au = au.view(au.dtype.newbyteorder())
3220
+ assert_(a.dtype.byteorder != au.dtype.byteorder)
3221
+ it = nditer(au, [], [['readwrite', 'updateifcopy']],
3222
+ casting='equiv', op_dtypes=[np.dtype('f4')])
3223
+ with it:
3224
+ it.operands[0][:] = 100
3225
+ assert_equal(au, 100)
3226
+ # do it again, this time raise an error,
3227
+ it = nditer(au, [], [['readwrite', 'updateifcopy']],
3228
+ casting='equiv', op_dtypes=[np.dtype('f4')])
3229
+ try:
3230
+ with it:
3231
+ assert_equal(au.flags.writeable, False)
3232
+ it.operands[0][:] = 0
3233
+ raise ValueError('exit context manager on exception')
3234
+ except Exception:
3235
+ pass
3236
+ assert_equal(au, 0)
3237
+ assert_equal(au.flags.writeable, True)
3238
+ # cannot reuse i outside context manager
3239
+ assert_raises(ValueError, getattr, it, 'operands')
3240
+
3241
+ it = nditer(au, [], [['readwrite', 'updateifcopy']],
3242
+ casting='equiv', op_dtypes=[np.dtype('f4')])
3243
+ with it:
3244
+ x = it.operands[0]
3245
+ x[:] = 6
3246
+ assert_(x.flags.writebackifcopy)
3247
+ assert_equal(au, 6)
3248
+ assert_(not x.flags.writebackifcopy)
3249
+ x[:] = 123 # x.data still valid
3250
+ assert_equal(au, 6) # but not connected to au
3251
+
3252
+ it = nditer(au, [],
3253
+ [['readwrite', 'updateifcopy']],
3254
+ casting='equiv', op_dtypes=[np.dtype('f4')])
3255
+ # reentering works
3256
+ with it:
3257
+ with it:
3258
+ for x in it:
3259
+ x[...] = 123
3260
+
3261
+ it = nditer(au, [],
3262
+ [['readwrite', 'updateifcopy']],
3263
+ casting='equiv', op_dtypes=[np.dtype('f4')])
3264
+ # make sure exiting the inner context manager closes the iterator
3265
+ with it:
3266
+ with it:
3267
+ for x in it:
3268
+ x[...] = 123
3269
+ assert_raises(ValueError, getattr, it, 'operands')
3270
+ # do not crash if original data array is decrefed
3271
+ it = nditer(au, [],
3272
+ [['readwrite', 'updateifcopy']],
3273
+ casting='equiv', op_dtypes=[np.dtype('f4')])
3274
+ del au
3275
+ with it:
3276
+ for x in it:
3277
+ x[...] = 123
3278
+ # make sure we cannot reenter the closed iterator
3279
+ enter = it.__enter__
3280
+ assert_raises(RuntimeError, enter)
3281
+
3282
+ def test_close_equivalent():
3283
+ ''' using a context amanger and using nditer.close are equivalent
3284
+ '''
3285
+ def add_close(x, y, out=None):
3286
+ addop = np.add
3287
+ it = np.nditer([x, y, out], [],
3288
+ [['readonly'], ['readonly'], ['writeonly', 'allocate']])
3289
+ for (a, b, c) in it:
3290
+ addop(a, b, out=c)
3291
+ ret = it.operands[2]
3292
+ it.close()
3293
+ return ret
3294
+
3295
+ def add_context(x, y, out=None):
3296
+ addop = np.add
3297
+ it = np.nditer([x, y, out], [],
3298
+ [['readonly'], ['readonly'], ['writeonly', 'allocate']])
3299
+ with it:
3300
+ for (a, b, c) in it:
3301
+ addop(a, b, out=c)
3302
+ return it.operands[2]
3303
+ z = add_close(range(5), range(5))
3304
+ assert_equal(z, range(0, 10, 2))
3305
+ z = add_context(range(5), range(5))
3306
+ assert_equal(z, range(0, 10, 2))
3307
+
3308
+ def test_close_raises():
3309
+ it = np.nditer(np.arange(3))
3310
+ assert_equal(next(it), 0)
3311
+ it.close()
3312
+ assert_raises(StopIteration, next, it)
3313
+ assert_raises(ValueError, getattr, it, 'operands')
3314
+
3315
+ def test_close_parameters():
3316
+ it = np.nditer(np.arange(3))
3317
+ assert_raises(TypeError, it.close, 1)
3318
+
3319
+ @pytest.mark.skipif(not HAS_REFCOUNT, reason="Python lacks refcounts")
3320
+ def test_warn_noclose():
3321
+ a = np.arange(6, dtype='f4')
3322
+ au = a.byteswap()
3323
+ au = au.view(au.dtype.newbyteorder())
3324
+ with pytest.warns(RuntimeWarning):
3325
+ it = np.nditer(au, [], [['readwrite', 'updateifcopy']],
3326
+ casting='equiv', op_dtypes=[np.dtype('f4')])
3327
+ del it
3328
+
3329
+ @pytest.mark.parametrize(["in_dtype", "buf_dtype"],
3330
+ [("i", "O"), ("O", "i"), # most simple cases
3331
+ ("i,O", "O,O"), # structured partially only copying O
3332
+ ("O,i", "i,O"), # structured casting to and from O
3333
+ ])
3334
+ @pytest.mark.parametrize("steps", [1, 2, 3])
3335
+ def test_partial_iteration_cleanup(in_dtype, buf_dtype, steps):
3336
+ """
3337
+ Checks for reference counting leaks during cleanup. Using explicit
3338
+ reference counts lead to occasional false positives (at least in parallel
3339
+ test setups). This test now should still test leaks correctly when
3340
+ run e.g. with pytest-valgrind or pytest-leaks
3341
+ """
3342
+ value = 2**30 + 1 # just a random value that Python won't intern
3343
+ arr = np.full(int(ncu.BUFSIZE * 2.5), value).astype(in_dtype)
3344
+
3345
+ it = np.nditer(arr, op_dtypes=[np.dtype(buf_dtype)],
3346
+ flags=["buffered", "external_loop", "refs_ok"], casting="unsafe")
3347
+ for step in range(steps):
3348
+ # The iteration finishes in 3 steps, the first two are partial
3349
+ next(it)
3350
+
3351
+ del it # not necessary, but we test the cleanup
3352
+
3353
+ # Repeat the test with `iternext`
3354
+ it = np.nditer(arr, op_dtypes=[np.dtype(buf_dtype)],
3355
+ flags=["buffered", "external_loop", "refs_ok"], casting="unsafe")
3356
+ for step in range(steps):
3357
+ it.iternext()
3358
+
3359
+ del it # not necessary, but we test the cleanup
3360
+
3361
+ @pytest.mark.skipif(not HAS_REFCOUNT, reason="Python lacks refcounts")
3362
+ @pytest.mark.parametrize(["in_dtype", "buf_dtype"],
3363
+ [("O", "i"), # most simple cases
3364
+ ("O,i", "i,O"), # structured casting to and from O
3365
+ ])
3366
+ def test_partial_iteration_error(in_dtype, buf_dtype):
3367
+ value = 123 # relies on python cache (leak-check will still find it)
3368
+ arr = np.full(int(ncu.BUFSIZE * 2.5), value).astype(in_dtype)
3369
+ if in_dtype == "O":
3370
+ arr[int(ncu.BUFSIZE * 1.5)] = None
3371
+ else:
3372
+ arr[int(ncu.BUFSIZE * 1.5)]["f0"] = None
3373
+
3374
+ count = sys.getrefcount(value)
3375
+
3376
+ it = np.nditer(arr, op_dtypes=[np.dtype(buf_dtype)],
3377
+ flags=["buffered", "external_loop", "refs_ok"], casting="unsafe")
3378
+ with pytest.raises(TypeError):
3379
+ # pytest.raises seems to have issues with the error originating
3380
+ # in the for loop, so manually unravel:
3381
+ next(it)
3382
+ next(it) # raises TypeError
3383
+
3384
+ # Repeat the test with `iternext` after resetting, the buffers should
3385
+ # already be cleared from any references, so resetting is sufficient.
3386
+ it.reset()
3387
+ with pytest.raises(TypeError):
3388
+ it.iternext()
3389
+ it.iternext()
3390
+
3391
+ assert count == sys.getrefcount(value)
3392
+
3393
+
3394
+ def test_arbitrary_number_of_ops():
3395
+ # 2*16 + 1 is still just a few kiB, so should be fast and easy to deal with
3396
+ # but larger than any small custom integer.
3397
+ ops = [np.arange(10) for a in range(2**16 + 1)]
3398
+
3399
+ it = np.nditer(ops)
3400
+ for i, vals in enumerate(it):
3401
+ assert all(v == i for v in vals)
3402
+
3403
+
3404
+ def test_arbitrary_number_of_ops_nested():
3405
+ # 2*16 + 1 is still just a few kiB, so should be fast and easy to deal with
3406
+ # but larger than any small custom integer.
3407
+ ops = [np.arange(10) for a in range(2**16 + 1)]
3408
+
3409
+ it = np.nested_iters(ops, [[0], []])
3410
+ for i, vals in enumerate(it):
3411
+ assert all(v == i for v in vals)
3412
+
3413
+
3414
+ @pytest.mark.slow
3415
+ @pytest.mark.skipif(not IS_64BIT, reason="test requires 64-bit system")
3416
+ @requires_memory(9 * np.iinfo(np.intc).max)
3417
+ @pytest.mark.thread_unsafe(reason="crashes with low memory")
3418
+ def test_arbitrary_number_of_ops_error():
3419
+ # A different error may happen for more than integer operands, but that
3420
+ # is too large to test nicely.
3421
+ a = np.ones(1)
3422
+ args = [a] * (np.iinfo(np.intc).max + 1)
3423
+ with pytest.raises(ValueError, match="Too many operands to nditer"):
3424
+ np.nditer(args)
3425
+
3426
+ with pytest.raises(ValueError, match="Too many operands to nditer"):
3427
+ np.nested_iters(args, [[0], []])
3428
+
3429
+
3430
+ @pytest.mark.thread_unsafe(reason="capfd is thread-unsafe")
3431
+ def test_debug_print(capfd):
3432
+ """
3433
+ Matches the expected output of a debug print with the actual output.
3434
+ Note that the iterator dump should not be considered stable API,
3435
+ this test is mainly to ensure the print does not crash.
3436
+
3437
+ Currently uses a subprocess to avoid dealing with the C level `printf`s.
3438
+ """
3439
+ # the expected output with all addresses and sizes stripped (they vary
3440
+ # and/or are platform dependent).
3441
+ expected = """
3442
+ ------ BEGIN ITERATOR DUMP ------
3443
+ | Iterator Address:
3444
+ | ItFlags: BUFFER REDUCE
3445
+ | NDim: 2
3446
+ | NOp: 2
3447
+ | IterSize: 50
3448
+ | IterStart: 0
3449
+ | IterEnd: 50
3450
+ | IterIndex: 0
3451
+ | Iterator SizeOf:
3452
+ | BufferData SizeOf:
3453
+ | AxisData SizeOf:
3454
+ |
3455
+ | Perm: 0 1
3456
+ | DTypes:
3457
+ | DTypes: dtype('float64') dtype('int32')
3458
+ | InitDataPtrs:
3459
+ | BaseOffsets: 0 0
3460
+ | Ptrs:
3461
+ | User/buffer ptrs:
3462
+ | Operands:
3463
+ | Operand DTypes: dtype('int64') dtype('float64')
3464
+ | OpItFlags:
3465
+ | Flags[0]: READ CAST
3466
+ | Flags[1]: READ WRITE CAST REDUCE
3467
+ |
3468
+ | BufferData:
3469
+ | BufferSize: 50
3470
+ | Size: 5
3471
+ | BufIterEnd: 5
3472
+ | BUFFER CoreSize: 5
3473
+ | REDUCE Pos: 0
3474
+ | REDUCE OuterSize: 10
3475
+ | REDUCE OuterDim: 1
3476
+ | Strides: 8 4
3477
+ | REDUCE Outer Strides: 40 0
3478
+ | REDUCE Outer Ptrs:
3479
+ | ReadTransferFn:
3480
+ | ReadTransferData:
3481
+ | WriteTransferFn:
3482
+ | WriteTransferData:
3483
+ | Buffers:
3484
+ |
3485
+ | AxisData[0]:
3486
+ | Shape: 5
3487
+ | Index: 0
3488
+ | Strides: 16 8
3489
+ | AxisData[1]:
3490
+ | Shape: 10
3491
+ | Index: 0
3492
+ | Strides: 80 0
3493
+ ------- END ITERATOR DUMP -------
3494
+ """.strip().splitlines()
3495
+
3496
+ arr1 = np.arange(100, dtype=np.int64).reshape(10, 10)[:, ::2]
3497
+ arr2 = np.arange(5.)
3498
+ it = np.nditer((arr1, arr2), op_dtypes=["d", "i4"], casting="unsafe",
3499
+ flags=["reduce_ok", "buffered"],
3500
+ op_flags=[["readonly"], ["readwrite"]])
3501
+ it.debug_print()
3502
+ res = capfd.readouterr().out
3503
+ res = res.strip().splitlines()
3504
+
3505
+ assert len(res) == len(expected)
3506
+ for res_line, expected_line in zip(res, expected):
3507
+ # The actual output may have additional pointers listed that are
3508
+ # stripped from the example output:
3509
+ assert res_line.startswith(expected_line.strip())
3510
+
3511
+
3512
+ @pytest.mark.skipif(sys.flags.optimize == 2, reason="Python running -OO")
3513
+ @pytest.mark.xfail(IS_PYPY, reason="PyPy does not modify tp_doc")
3514
+ def test_signature_constructor():
3515
+ sig = inspect.signature(np.nditer)
3516
+
3517
+ assert sig.parameters
3518
+ assert "self" not in sig.parameters
3519
+ assert "args" not in sig.parameters
3520
+ assert "kwargs" not in sig.parameters
3521
+
3522
+
3523
+ @pytest.mark.skipif(sys.flags.optimize == 2, reason="Python running -OO")
3524
+ @pytest.mark.xfail(IS_PYPY, reason="PyPy does not modify tp_doc")
3525
+ @pytest.mark.parametrize(
3526
+ "method",
3527
+ [fn for name, fn in vars(np.nditer).items() if callable(fn) and name[0] != "_"],
3528
+ )
3529
+ def test_signature_methods(method):
3530
+ sig = inspect.signature(method)
3531
+
3532
+ assert "self" in sig.parameters
3533
+ assert sig.parameters["self"].kind is inspect.Parameter.POSITIONAL_ONLY