2
1
/* Should only be used if x is known to be an nd-array */
3
2
#define _ARET(x) PyArray_Return((PyArrayObject *)(x))
6
5
array_take(PyArrayObject *self, PyObject *args, PyObject *kwds)
8
int dimension=MAX_DIMS;
10
PyArrayObject *out=NULL;
11
NPY_CLIPMODE mode=NPY_RAISE;
12
static char *kwlist[] = {"indices", "axis", "out", "mode", NULL};
14
if (!PyArg_ParseTupleAndKeywords(args, kwds, "O|O&O&O&", kwlist,
15
&indices, PyArray_AxisConverter,
17
PyArray_OutputConverter,
19
PyArray_ClipmodeConverter,
23
return _ARET(PyArray_TakeFrom(self, indices, dimension, out, mode));
7
int dimension=MAX_DIMS;
9
PyArrayObject *out=NULL;
10
NPY_CLIPMODE mode=NPY_RAISE;
11
static char *kwlist[] = {"indices", "axis", "out", "mode", NULL};
13
if (!PyArg_ParseTupleAndKeywords(args, kwds, "O|O&O&O&", kwlist,
14
&indices, PyArray_AxisConverter,
16
PyArray_OutputConverter,
18
PyArray_ClipmodeConverter,
22
return _ARET(PyArray_TakeFrom(self, indices, dimension, out, mode));
27
26
array_fill(PyArrayObject *self, PyObject *args)
30
if (!PyArg_ParseTuple(args, "O", &obj))
32
if (PyArray_FillWithScalar(self, obj) < 0) return NULL;
29
if (!PyArg_ParseTuple(args, "O", &obj))
31
if (PyArray_FillWithScalar(self, obj) < 0) return NULL;
38
37
array_put(PyArrayObject *self, PyObject *args, PyObject *kwds)
40
PyObject *indices, *values;
41
NPY_CLIPMODE mode=NPY_RAISE;
42
static char *kwlist[] = {"indices", "values", "mode", NULL};
39
PyObject *indices, *values;
40
NPY_CLIPMODE mode=NPY_RAISE;
41
static char *kwlist[] = {"indices", "values", "mode", NULL};
44
if (!PyArg_ParseTupleAndKeywords(args, kwds, "OO|O&", kwlist,
46
PyArray_ClipmodeConverter,
49
return PyArray_PutTo(self, values, indices, mode);
43
if (!PyArg_ParseTupleAndKeywords(args, kwds, "OO|O&", kwlist,
45
PyArray_ClipmodeConverter,
48
return PyArray_PutTo(self, values, indices, mode);
53
52
array_reshape(PyArrayObject *self, PyObject *args, PyObject *kwds)
55
PyArray_Dims newshape;
57
PyArray_ORDER order=PyArray_CORDER;
62
ref = PyDict_GetItemString(kwds, "order");
64
PyErr_SetString(PyExc_TypeError,
65
"invalid keyword argument");
68
if ((PyArray_OrderConverter(ref, &order) == PY_FAIL))
72
n = PyTuple_Size(args);
74
if (PyTuple_GET_ITEM(args, 0) == Py_None)
75
return PyArray_View(self, NULL, NULL);
76
if (!PyArg_ParseTuple(args, "O&", PyArray_IntpConverter,
77
&newshape)) return NULL;
80
if (!PyArray_IntpConverter(args, &newshape)) {
81
if (!PyErr_Occurred()) {
82
PyErr_SetString(PyExc_TypeError,
88
ret = PyArray_Newshape(self, &newshape, order);
89
PyDimMem_FREE(newshape.ptr);
54
PyArray_Dims newshape;
56
PyArray_ORDER order=PyArray_CORDER;
61
ref = PyDict_GetItemString(kwds, "order");
63
PyErr_SetString(PyExc_TypeError,
64
"invalid keyword argument");
67
if ((PyArray_OrderConverter(ref, &order) == PY_FAIL))
71
n = PyTuple_Size(args);
73
if (PyTuple_GET_ITEM(args, 0) == Py_None)
74
return PyArray_View(self, NULL, NULL);
75
if (!PyArg_ParseTuple(args, "O&", PyArray_IntpConverter,
76
&newshape)) return NULL;
79
if (!PyArray_IntpConverter(args, &newshape)) {
80
if (!PyErr_Occurred()) {
81
PyErr_SetString(PyExc_TypeError,
87
ret = PyArray_Newshape(self, &newshape, order);
88
PyDimMem_FREE(newshape.ptr);
93
PyDimMem_FREE(newshape.ptr);
92
PyDimMem_FREE(newshape.ptr);
98
97
array_squeeze(PyArrayObject *self, PyObject *args)
100
if (!PyArg_ParseTuple(args, "")) return NULL;
101
return PyArray_Squeeze(self);
99
if (!PyArg_ParseTuple(args, "")) return NULL;
100
return PyArray_Squeeze(self);
104
103
static PyObject *
105
array_view(PyArrayObject *self, PyObject *args)
104
array_view(PyArrayObject *self, PyObject *args, PyObject *kwds)
107
PyObject *otype=NULL;
108
PyArray_Descr *type=NULL;
110
if (!PyArg_ParseTuple(args, "|O", &otype)) return NULL;
113
if (PyType_Check(otype) && \
114
PyType_IsSubtype((PyTypeObject *)otype,
116
return PyArray_View(self, NULL,
117
(PyTypeObject *)otype);
120
if (PyArray_DescrConverter(otype, &type) == PY_FAIL)
124
return PyArray_View(self, type, NULL);
106
PyObject *out_dtype=NULL;
107
PyObject *out_type=NULL;
108
PyArray_Descr *dtype=NULL;
110
static char *kwlist[] = {"dtype", "type", NULL};
111
if (!PyArg_ParseTupleAndKeywords(args, kwds, "|OO", kwlist,
116
/* If user specified a positional argument, guess whether it
117
represents a type or a dtype for backward compatibility. */
119
/* type specified? */
120
if (PyType_Check(out_dtype) &&
121
PyType_IsSubtype((PyTypeObject *)out_dtype,
124
PyErr_SetString(PyExc_ValueError,
125
"Cannot specify output type twice.");
128
out_type = out_dtype;
133
if ((out_type) && (!PyType_Check(out_type) ||
134
!PyType_IsSubtype((PyTypeObject *)out_type,
136
PyErr_SetString(PyExc_ValueError,
137
"Type must be a sub-type of ndarray type");
142
(PyArray_DescrConverter(out_dtype, &dtype) == PY_FAIL)) {
143
PyErr_SetString(PyExc_ValueError,
144
"Dtype must be a numpy data-type");
148
return PyArray_View(self, dtype, (PyTypeObject*)out_type);
127
151
static PyObject *
128
152
array_argmax(PyArrayObject *self, PyObject *args, PyObject *kwds)
131
PyArrayObject *out=NULL;
132
static char *kwlist[] = {"axis", "out", NULL};
134
if (!PyArg_ParseTupleAndKeywords(args, kwds, "|O&O&", kwlist,
135
PyArray_AxisConverter,
137
PyArray_OutputConverter,
141
return _ARET(PyArray_ArgMax(self, axis, out));
155
PyArrayObject *out=NULL;
156
static char *kwlist[] = {"axis", "out", NULL};
158
if (!PyArg_ParseTupleAndKeywords(args, kwds, "|O&O&", kwlist,
159
PyArray_AxisConverter,
161
PyArray_OutputConverter,
165
return _ARET(PyArray_ArgMax(self, axis, out));
144
168
static PyObject *
145
169
array_argmin(PyArrayObject *self, PyObject *args, PyObject *kwds)
148
PyArrayObject *out=NULL;
149
static char *kwlist[] = {"axis", "out", NULL};
151
if (!PyArg_ParseTupleAndKeywords(args, kwds, "|O&O&", kwlist,
152
PyArray_AxisConverter,
154
PyArray_OutputConverter,
158
return _ARET(PyArray_ArgMin(self, axis, out));
172
PyArrayObject *out=NULL;
173
static char *kwlist[] = {"axis", "out", NULL};
175
if (!PyArg_ParseTupleAndKeywords(args, kwds, "|O&O&", kwlist,
176
PyArray_AxisConverter,
178
PyArray_OutputConverter,
182
return _ARET(PyArray_ArgMin(self, axis, out));
161
185
static PyObject *
162
186
array_max(PyArrayObject *self, PyObject *args, PyObject *kwds)
165
PyArrayObject *out=NULL;
166
static char *kwlist[] = {"axis", "out", NULL};
168
if (!PyArg_ParseTupleAndKeywords(args, kwds, "|O&O&", kwlist,
169
PyArray_AxisConverter,
171
PyArray_OutputConverter,
175
return PyArray_Max(self, axis, out);
189
PyArrayObject *out=NULL;
190
static char *kwlist[] = {"axis", "out", NULL};
192
if (!PyArg_ParseTupleAndKeywords(args, kwds, "|O&O&", kwlist,
193
PyArray_AxisConverter,
195
PyArray_OutputConverter,
199
return PyArray_Max(self, axis, out);
178
202
static PyObject *
179
203
array_ptp(PyArrayObject *self, PyObject *args, PyObject *kwds)
182
PyArrayObject *out=NULL;
183
static char *kwlist[] = {"axis", "out", NULL};
185
if (!PyArg_ParseTupleAndKeywords(args, kwds, "|O&O&", kwlist,
186
PyArray_AxisConverter,
188
PyArray_OutputConverter,
192
return PyArray_Ptp(self, axis, out);
206
PyArrayObject *out=NULL;
207
static char *kwlist[] = {"axis", "out", NULL};
209
if (!PyArg_ParseTupleAndKeywords(args, kwds, "|O&O&", kwlist,
210
PyArray_AxisConverter,
212
PyArray_OutputConverter,
216
return PyArray_Ptp(self, axis, out);
196
220
static PyObject *
197
221
array_min(PyArrayObject *self, PyObject *args, PyObject *kwds)
200
PyArrayObject *out=NULL;
201
static char *kwlist[] = {"axis", "out", NULL};
203
if (!PyArg_ParseTupleAndKeywords(args, kwds, "|O&O&", kwlist,
204
PyArray_AxisConverter,
206
PyArray_OutputConverter,
210
return PyArray_Min(self, axis, out);
224
PyArrayObject *out=NULL;
225
static char *kwlist[] = {"axis", "out", NULL};
227
if (!PyArg_ParseTupleAndKeywords(args, kwds, "|O&O&", kwlist,
228
PyArray_AxisConverter,
230
PyArray_OutputConverter,
234
return PyArray_Min(self, axis, out);
213
237
static PyObject *
214
238
array_swapaxes(PyArrayObject *self, PyObject *args)
218
if (!PyArg_ParseTuple(args, "ii", &axis1, &axis2)) return NULL;
220
return PyArray_SwapAxes(self, axis1, axis2);
242
if (!PyArg_ParseTuple(args, "ii", &axis1, &axis2)) return NULL;
244
return PyArray_SwapAxes(self, axis1, axis2);
224
248
/* steals typed reference */
226
Get a subset of bytes from each element of the array
250
Get a subset of bytes from each element of the array
228
252
static PyObject *
229
253
PyArray_GetField(PyArrayObject *self, PyArray_Descr *typed, int offset)
233
if (offset < 0 || (offset + typed->elsize) > self->descr->elsize) {
234
PyErr_Format(PyExc_ValueError,
235
"Need 0 <= offset <= %d for requested type " \
236
"but received offset = %d",
237
self->descr->elsize-typed->elsize, offset);
241
ret = PyArray_NewFromDescr(self->ob_type,
243
self->nd, self->dimensions,
246
self->flags, (PyObject *)self);
247
if (ret == NULL) return NULL;
249
((PyArrayObject *)ret)->base = (PyObject *)self;
251
PyArray_UpdateFlags((PyArrayObject *)ret, UPDATE_ALL);
257
if (offset < 0 || (offset + typed->elsize) > self->descr->elsize) {
258
PyErr_Format(PyExc_ValueError,
259
"Need 0 <= offset <= %d for requested type " \
260
"but received offset = %d",
261
self->descr->elsize-typed->elsize, offset);
265
ret = PyArray_NewFromDescr(self->ob_type,
267
self->nd, self->dimensions,
270
self->flags, (PyObject *)self);
271
if (ret == NULL) return NULL;
273
((PyArrayObject *)ret)->base = (PyObject *)self;
275
PyArray_UpdateFlags((PyArrayObject *)ret, UPDATE_ALL);
255
279
static PyObject *
256
280
array_getfield(PyArrayObject *self, PyObject *args, PyObject *kwds)
259
PyArray_Descr *dtype;
261
static char *kwlist[] = {"dtype", "offset", 0};
263
if (!PyArg_ParseTupleAndKeywords(args, kwds, "O&|i", kwlist,
264
PyArray_DescrConverter,
265
&dtype, &offset)) return NULL;
267
return _ARET(PyArray_GetField(self, dtype, offset));
283
PyArray_Descr *dtype=NULL;
285
static char *kwlist[] = {"dtype", "offset", 0};
287
if (!PyArg_ParseTupleAndKeywords(args, kwds, "O&|i", kwlist,
288
PyArray_DescrConverter,
294
return PyArray_GetField(self, dtype, offset);
272
Set a subset of bytes from each element of the array
299
Set a subset of bytes from each element of the array
275
302
PyArray_SetField(PyArrayObject *self, PyArray_Descr *dtype,
276
int offset, PyObject *val)
303
int offset, PyObject *val)
281
if (offset < 0 || (offset + dtype->elsize) > self->descr->elsize) {
282
PyErr_Format(PyExc_ValueError,
283
"Need 0 <= offset <= %d for requested type " \
284
"but received offset = %d",
285
self->descr->elsize-dtype->elsize, offset);
289
ret = PyArray_NewFromDescr(self->ob_type,
290
dtype, self->nd, self->dimensions,
291
self->strides, self->data + offset,
292
self->flags, (PyObject *)self);
293
if (ret == NULL) return -1;
295
((PyArrayObject *)ret)->base = (PyObject *)self;
297
PyArray_UpdateFlags((PyArrayObject *)ret, UPDATE_ALL);
298
retval = PyArray_CopyObject((PyArrayObject *)ret, val);
308
if (offset < 0 || (offset + dtype->elsize) > self->descr->elsize) {
309
PyErr_Format(PyExc_ValueError,
310
"Need 0 <= offset <= %d for requested type " \
311
"but received offset = %d",
312
self->descr->elsize-dtype->elsize, offset);
316
ret = PyArray_NewFromDescr(self->ob_type,
317
dtype, self->nd, self->dimensions,
318
self->strides, self->data + offset,
319
self->flags, (PyObject *)self);
320
if (ret == NULL) return -1;
322
((PyArrayObject *)ret)->base = (PyObject *)self;
324
PyArray_UpdateFlags((PyArrayObject *)ret, UPDATE_ALL);
325
retval = PyArray_CopyObject((PyArrayObject *)ret, val);
303
330
static PyObject *
304
331
array_setfield(PyArrayObject *self, PyObject *args, PyObject *kwds)
306
PyArray_Descr *dtype;
309
static char *kwlist[] = {"value", "dtype", "offset", 0};
311
if (!PyArg_ParseTupleAndKeywords(args, kwds, "OO&|i", kwlist,
312
&value, PyArray_DescrConverter,
313
&dtype, &offset)) return NULL;
315
if (PyArray_SetField(self, dtype, offset, value) < 0)
333
PyArray_Descr *dtype=NULL;
336
static char *kwlist[] = {"value", "dtype", "offset", 0};
338
if (!PyArg_ParseTupleAndKeywords(args, kwds, "OO&|i", kwlist,
339
&value, PyArray_DescrConverter,
345
if (PyArray_SetField(self, dtype, offset, value) < 0)
321
351
/* This doesn't change the descriptor just the actual data...
325
355
static PyObject *
326
356
PyArray_Byteswap(PyArrayObject *self, Bool inplace)
330
PyArray_CopySwapNFunc *copyswapn;
331
PyArrayIterObject *it;
333
copyswapn = self->descr->f->copyswapn;
335
if (!PyArray_ISWRITEABLE(self)) {
336
PyErr_SetString(PyExc_RuntimeError,
337
"Cannot byte-swap in-place on a " \
341
size = PyArray_SIZE(self);
342
if (PyArray_ISONESEGMENT(self)) {
343
copyswapn(self->data, self->descr->elsize, NULL, -1, size, 1, self);
345
else { /* Use iterator */
348
it = (PyArrayIterObject *) \
349
PyArray_IterAllButAxis((PyObject *)self, &axis);
350
stride = self->strides[axis];
351
size = self->dimensions[axis];
352
while (it->index < it->size) {
353
copyswapn(it->dataptr, stride, NULL, -1, size, 1, self);
354
PyArray_ITER_NEXT(it);
360
return (PyObject *)self;
364
if ((ret = (PyArrayObject *)PyArray_NewCopy(self,-1)) == NULL)
366
new = PyArray_Byteswap(ret, TRUE);
368
return (PyObject *)ret;
360
PyArray_CopySwapNFunc *copyswapn;
361
PyArrayIterObject *it;
363
copyswapn = self->descr->f->copyswapn;
365
if (!PyArray_ISWRITEABLE(self)) {
366
PyErr_SetString(PyExc_RuntimeError,
367
"Cannot byte-swap in-place on a " \
371
size = PyArray_SIZE(self);
372
if (PyArray_ISONESEGMENT(self)) {
373
copyswapn(self->data, self->descr->elsize, NULL, -1, size, 1, self);
375
else { /* Use iterator */
378
it = (PyArrayIterObject *) \
379
PyArray_IterAllButAxis((PyObject *)self, &axis);
380
stride = self->strides[axis];
381
size = self->dimensions[axis];
382
while (it->index < it->size) {
383
copyswapn(it->dataptr, stride, NULL, -1, size, 1, self);
384
PyArray_ITER_NEXT(it);
390
return (PyObject *)self;
394
if ((ret = (PyArrayObject *)PyArray_NewCopy(self,-1)) == NULL)
396
new = PyArray_Byteswap(ret, TRUE);
398
return (PyObject *)ret;
373
403
static PyObject *
374
404
array_byteswap(PyArrayObject *self, PyObject *args)
378
if (!PyArg_ParseTuple(args, "|O&", PyArray_BoolConverter, &inplace))
381
return PyArray_Byteswap(self, inplace);
408
if (!PyArg_ParseTuple(args, "|O&", PyArray_BoolConverter, &inplace))
411
return PyArray_Byteswap(self, inplace);
384
414
static PyObject *
385
415
array_tolist(PyArrayObject *self, PyObject *args)
387
if (!PyArg_ParseTuple(args, "")) return NULL;
388
return PyArray_ToList(self);
417
if (!PyArg_ParseTuple(args, "")) return NULL;
418
return PyArray_ToList(self);
392
422
static PyObject *
393
423
array_tostring(PyArrayObject *self, PyObject *args, PyObject *kwds)
395
NPY_ORDER order=NPY_CORDER;
396
static char *kwlist[] = {"order", NULL};
425
NPY_ORDER order=NPY_CORDER;
426
static char *kwlist[] = {"order", NULL};
398
if (!PyArg_ParseTupleAndKeywords(args, kwds, "|O&", kwlist,
399
PyArray_OrderConverter,
400
&order)) return NULL;
401
return PyArray_ToString(self, order);
428
if (!PyArg_ParseTupleAndKeywords(args, kwds, "|O&", kwlist,
429
PyArray_OrderConverter,
430
&order)) return NULL;
431
return PyArray_ToString(self, order);
408
438
static PyObject *
409
439
array_tofile(PyArrayObject *self, PyObject *args, PyObject *kwds)
416
static char *kwlist[] = {"file", "sep", "format", NULL};
418
if (!PyArg_ParseTupleAndKeywords(args, kwds, "O|ss", kwlist,
419
&file, &sep, &format)) return NULL;
421
if (PyString_Check(file) || PyUnicode_Check(file)) {
422
file = PyObject_CallFunction((PyObject *)&PyFile_Type,
424
if (file==NULL) return NULL;
429
fd = PyFile_AsFile(file);
431
PyErr_SetString(PyExc_IOError, "first argument must be a " \
432
"string or open file");
436
ret = PyArray_ToFile(self, fd, sep, format);
438
if (ret < 0) return NULL;
446
static char *kwlist[] = {"file", "sep", "format", NULL};
448
if (!PyArg_ParseTupleAndKeywords(args, kwds, "O|ss", kwlist,
449
&file, &sep, &format)) return NULL;
451
if (PyString_Check(file) || PyUnicode_Check(file)) {
452
file = PyObject_CallFunction((PyObject *)&PyFile_Type,
454
if (file==NULL) return NULL;
459
fd = PyFile_AsFile(file);
461
PyErr_SetString(PyExc_IOError, "first argument must be a " \
462
"string or open file");
466
ret = PyArray_ToFile(self, fd, sep, format);
468
if (ret < 0) return NULL;
444
474
static PyObject *
445
475
array_toscalar(PyArrayObject *self, PyObject *args) {
447
n = PyTuple_GET_SIZE(args);
451
obj = PyTuple_GET_ITEM(args, 0);
452
if (PyTuple_Check(obj)) {
454
n = PyTuple_GET_SIZE(args);
459
if (self->nd == 0 || PyArray_SIZE(self) == 1)
460
return self->descr->f->getitem(self->data, self);
462
PyErr_SetString(PyExc_ValueError,
463
"can only convert an array " \
464
" of size 1 to a Python scalar");
468
else if (n != self->nd && (n > 1 || self->nd==0)) {
469
PyErr_SetString(PyExc_ValueError,
470
"incorrect number of indices for " \
477
n = PyTuple_GET_SIZE(args);
481
obj = PyTuple_GET_ITEM(args, 0);
482
if (PyTuple_Check(obj)) {
484
n = PyTuple_GET_SIZE(args);
489
if (self->nd == 0 || PyArray_SIZE(self) == 1)
490
return self->descr->f->getitem(self->data, self);
492
PyErr_SetString(PyExc_ValueError,
493
"can only convert an array " \
494
" of size 1 to a Python scalar");
498
else if (n != self->nd && (n > 1 || self->nd==0)) {
499
PyErr_SetString(PyExc_ValueError,
500
"incorrect number of indices for " \
504
else if (n==1) { /* allows for flat getting as well as 1-d case */
505
intp value, loc, index, factor;
506
intp factors[MAX_DIMS];
507
value = PyArray_PyIntAsIntp(PyTuple_GET_ITEM(args, 0));
508
if (error_converting(value)) {
509
PyErr_SetString(PyExc_ValueError, "invalid integer");
512
factor = PyArray_SIZE(self);
513
if (value < 0) value += factor;
514
if ((value >= factor) || (value < 0)) {
515
PyErr_SetString(PyExc_ValueError,
516
"index out of bounds");
520
value *= self->strides[0];
521
return self->descr->f->getitem(self->data + value,
527
factors[nd] = factor;
528
factor *= self->dimensions[nd];
531
for (nd=0; nd < self->nd; nd++) {
532
index = value / factors[nd];
533
value = value % factors[nd];
534
loc += self->strides[nd]*index;
537
return self->descr->f->getitem(self->data + loc,
542
intp loc, index[MAX_DIMS];
543
nd = PyArray_IntpFromSequence(args, index, MAX_DIMS);
544
if (nd < n) return NULL;
548
index[nd] += self->dimensions[nd];
550
index[nd] >= self->dimensions[nd]) {
551
PyErr_SetString(PyExc_ValueError,
552
"index out of bounds");
474
else if (n==1) { /* allows for flat getting as well as 1-d case */
475
intp value, loc, index, factor;
476
intp factors[MAX_DIMS];
477
value = PyArray_PyIntAsIntp(PyTuple_GET_ITEM(args, 0));
478
if (error_converting(value)) {
479
PyErr_SetString(PyExc_ValueError, "invalid integer");
482
if (value >= PyArray_SIZE(self)) {
483
PyErr_SetString(PyExc_ValueError,
484
"index out of bounds");
488
value *= self->strides[0];
489
return self->descr->f->getitem(self->data + value,
495
factors[nd] = factor;
496
factor *= self->dimensions[nd];
499
for (nd=0; nd < self->nd; nd++) {
500
index = value / factors[nd];
501
value = value % factors[nd];
502
loc += self->strides[nd]*index;
505
return self->descr->f->getitem(self->data + loc,
510
intp loc, index[MAX_DIMS];
511
nd = PyArray_IntpFromSequence(args, index, MAX_DIMS);
512
if (nd < n) return NULL;
516
index[nd] += self->dimensions[nd];
518
index[nd] >= self->dimensions[nd]) {
519
PyErr_SetString(PyExc_ValueError,
520
"index out of bounds");
523
loc += self->strides[nd]*index[nd];
525
return self->descr->f->getitem(self->data + loc, self);
555
loc += self->strides[nd]*index[nd];
557
return self->descr->f->getitem(self->data + loc, self);
529
561
static PyObject *
530
562
array_setscalar(PyArrayObject *self, PyObject *args) {
534
n = PyTuple_GET_SIZE(args)-1;
537
PyErr_SetString(PyExc_ValueError,
538
"itemset must have at least one argument");
541
obj = PyTuple_GET_ITEM(args, n);
543
if (self->nd == 0 || PyArray_SIZE(self) == 1) {
544
ret = self->descr->f->setitem(obj, self->data, self);
547
PyErr_SetString(PyExc_ValueError,
548
"can only place a scalar for an "
553
else if (n != self->nd && (n > 1 || self->nd==0)) {
554
PyErr_SetString(PyExc_ValueError,
555
"incorrect number of indices for " \
559
else if (n==1) { /* allows for flat setting as well as 1-d case */
560
intp value, loc, index, factor;
561
intp factors[MAX_DIMS];
566
n = PyTuple_GET_SIZE(args)-1;
564
indobj = PyTuple_GET_ITEM(args, 0);
565
if (PyTuple_Check(indobj)) {
570
nn = PyTuple_GET_SIZE(indobj);
571
newargs = PyTuple_New(nn+1);
573
for (i=0; i<nn; i++) {
574
tmp = PyTuple_GET_ITEM(indobj, i);
576
PyTuple_SET_ITEM(newargs, i, tmp);
578
PyTuple_SET_ITEM(newargs, nn, obj);
579
/* Call with a converted set of arguments */
580
res = array_setscalar(self, newargs);
584
value = PyArray_PyIntAsIntp(indobj);
585
if (error_converting(value)) {
586
PyErr_SetString(PyExc_ValueError, "invalid integer");
589
if (value >= PyArray_SIZE(self)) {
590
PyErr_SetString(PyExc_ValueError,
591
"index out of bounds");
595
value *= self->strides[0];
596
ret = self->descr->f->setitem(obj, self->data + value,
603
factors[nd] = factor;
604
factor *= self->dimensions[nd];
607
for (nd=0; nd < self->nd; nd++) {
608
index = value / factors[nd];
609
value = value % factors[nd];
610
loc += self->strides[nd]*index;
613
ret = self->descr->f->setitem(obj, self->data + loc, self);
569
PyErr_SetString(PyExc_ValueError,
570
"itemset must have at least one argument");
573
obj = PyTuple_GET_ITEM(args, n);
575
if (self->nd == 0 || PyArray_SIZE(self) == 1) {
576
ret = self->descr->f->setitem(obj, self->data, self);
616
intp loc, index[MAX_DIMS];
618
tupargs = PyTuple_GetSlice(args, 1, n+1);
619
nd = PyArray_IntpFromSequence(tupargs, index, MAX_DIMS);
621
if (nd < n) return NULL;
625
index[nd] += self->dimensions[nd];
627
index[nd] >= self->dimensions[nd]) {
628
PyErr_SetString(PyExc_ValueError,
629
"index out of bounds");
632
loc += self->strides[nd]*index[nd];
634
ret = self->descr->f->setitem(obj, self->data + loc, self);
579
PyErr_SetString(PyExc_ValueError,
580
"can only place a scalar for an "
585
else if (n != self->nd && (n > 1 || self->nd==0)) {
586
PyErr_SetString(PyExc_ValueError,
587
"incorrect number of indices for " \
591
else if (n==1) { /* allows for flat setting as well as 1-d case */
592
intp value, loc, index, factor;
593
intp factors[MAX_DIMS];
596
indobj = PyTuple_GET_ITEM(args, 0);
597
if (PyTuple_Check(indobj)) {
602
nn = PyTuple_GET_SIZE(indobj);
603
newargs = PyTuple_New(nn+1);
605
for (i=0; i<nn; i++) {
606
tmp = PyTuple_GET_ITEM(indobj, i);
608
PyTuple_SET_ITEM(newargs, i, tmp);
610
PyTuple_SET_ITEM(newargs, nn, obj);
611
/* Call with a converted set of arguments */
612
res = array_setscalar(self, newargs);
616
value = PyArray_PyIntAsIntp(indobj);
617
if (error_converting(value)) {
618
PyErr_SetString(PyExc_ValueError, "invalid integer");
621
if (value >= PyArray_SIZE(self)) {
622
PyErr_SetString(PyExc_ValueError,
623
"index out of bounds");
627
value *= self->strides[0];
628
ret = self->descr->f->setitem(obj, self->data + value,
635
factors[nd] = factor;
636
factor *= self->dimensions[nd];
639
for (nd=0; nd < self->nd; nd++) {
640
index = value / factors[nd];
641
value = value % factors[nd];
642
loc += self->strides[nd]*index;
645
ret = self->descr->f->setitem(obj, self->data + loc, self);
648
intp loc, index[MAX_DIMS];
650
tupargs = PyTuple_GetSlice(args, 0, n);
651
nd = PyArray_IntpFromSequence(tupargs, index, MAX_DIMS);
653
if (nd < n) return NULL;
657
index[nd] += self->dimensions[nd];
659
index[nd] >= self->dimensions[nd]) {
660
PyErr_SetString(PyExc_ValueError,
661
"index out of bounds");
664
loc += self->strides[nd]*index[nd];
666
ret = self->descr->f->setitem(obj, self->data + loc, self);
638
if (ret < 0) return NULL;
670
if (ret < 0) return NULL;
644
676
static PyObject *
645
677
array_cast(PyArrayObject *self, PyObject *args)
647
PyArray_Descr *descr=NULL;
650
if (!PyArg_ParseTuple(args, "O&", PyArray_DescrConverter,
651
&descr)) return NULL;
653
if (descr == self->descr) {
654
obj = _ARET(PyArray_NewCopy(self,0));
658
if (descr->names != NULL) {
659
return PyArray_FromArray(self, descr, NPY_FORCECAST);
661
return PyArray_CastToType(self, descr, 0);
679
PyArray_Descr *descr=NULL;
682
if (!PyArg_ParseTuple(args, "O&", PyArray_DescrConverter,
688
if (PyArray_EquivTypes(descr, self->descr)) {
689
obj = _ARET(PyArray_NewCopy(self,NPY_ANYORDER));
693
if (descr->names != NULL) {
695
flags = NPY_FORCECAST;
696
if (PyArray_ISFORTRAN(self)) {
697
flags |= NPY_FORTRAN;
699
return PyArray_FromArray(self, descr, flags);
701
return PyArray_CastToType(self, descr, PyArray_ISFORTRAN(self));
664
704
/* default sub-type implementation */
667
707
static PyObject *
668
708
array_wraparray(PyArrayObject *self, PyObject *args)
673
if (PyTuple_Size(args) < 1) {
674
PyErr_SetString(PyExc_TypeError,
675
"only accepts 1 argument");
678
arr = PyTuple_GET_ITEM(args, 0);
679
if (!PyArray_Check(arr)) {
680
PyErr_SetString(PyExc_TypeError,
681
"can only be called with ndarray object");
685
Py_INCREF(PyArray_DESCR(arr));
686
ret = PyArray_NewFromDescr(self->ob_type,
690
PyArray_STRIDES(arr), PyArray_DATA(arr),
691
PyArray_FLAGS(arr), (PyObject *)self);
692
if (ret == NULL) return NULL;
694
PyArray_BASE(ret) = arr;
713
if (PyTuple_Size(args) < 1) {
714
PyErr_SetString(PyExc_TypeError,
715
"only accepts 1 argument");
718
arr = PyTuple_GET_ITEM(args, 0);
719
if (!PyArray_Check(arr)) {
720
PyErr_SetString(PyExc_TypeError,
721
"can only be called with ndarray object");
725
Py_INCREF(PyArray_DESCR(arr));
726
ret = PyArray_NewFromDescr(self->ob_type,
730
PyArray_STRIDES(arr), PyArray_DATA(arr),
731
PyArray_FLAGS(arr), (PyObject *)self);
732
if (ret == NULL) return NULL;
734
PyArray_BASE(ret) = arr;
699
739
static PyObject *
700
740
array_getarray(PyArrayObject *self, PyObject *args)
702
PyArray_Descr *newtype=NULL;
705
if (!PyArg_ParseTuple(args, "|O&", PyArray_DescrConverter,
706
&newtype)) return NULL;
708
/* convert to PyArray_Type */
709
if (!PyArray_CheckExact(self)) {
711
PyTypeObject *subtype = &PyArray_Type;
713
if (!PyType_IsSubtype(self->ob_type, &PyArray_Type)) {
714
subtype = &PyArray_Type;
717
Py_INCREF(PyArray_DESCR(self));
718
new = PyArray_NewFromDescr(subtype,
722
PyArray_STRIDES(self),
724
PyArray_FLAGS(self), NULL);
725
if (new == NULL) return NULL;
727
PyArray_BASE(new) = (PyObject *)self;
728
self = (PyArrayObject *)new;
734
if ((newtype == NULL) || \
735
PyArray_EquivTypes(self->descr, newtype)) {
736
return (PyObject *)self;
739
ret = PyArray_CastToType(self, newtype, 0);
742
PyArray_Descr *newtype=NULL;
745
if (!PyArg_ParseTuple(args, "|O&", PyArray_DescrConverter,
751
/* convert to PyArray_Type */
752
if (!PyArray_CheckExact(self)) {
754
PyTypeObject *subtype = &PyArray_Type;
756
if (!PyType_IsSubtype(self->ob_type, &PyArray_Type)) {
757
subtype = &PyArray_Type;
760
Py_INCREF(PyArray_DESCR(self));
761
new = PyArray_NewFromDescr(subtype,
765
PyArray_STRIDES(self),
767
PyArray_FLAGS(self), NULL);
768
if (new == NULL) return NULL;
770
PyArray_BASE(new) = (PyObject *)self;
771
self = (PyArrayObject *)new;
777
if ((newtype == NULL) || \
778
PyArray_EquivTypes(self->descr, newtype)) {
779
return (PyObject *)self;
782
ret = PyArray_CastToType(self, newtype, 0);
746
789
static PyObject *
747
790
array_copy(PyArrayObject *self, PyObject *args)
749
PyArray_ORDER fortran=PyArray_CORDER;
750
if (!PyArg_ParseTuple(args, "|O&", PyArray_OrderConverter,
751
&fortran)) return NULL;
792
PyArray_ORDER fortran=PyArray_CORDER;
793
if (!PyArg_ParseTuple(args, "|O&", PyArray_OrderConverter,
794
&fortran)) return NULL;
753
return PyArray_NewCopy(self, fortran);
796
return PyArray_NewCopy(self, fortran);
757
800
static PyObject *
758
801
array_resize(PyArrayObject *self, PyObject *args, PyObject *kwds)
760
PyArray_Dims newshape;
764
PyArray_ORDER fortran=PyArray_ANYORDER;
803
PyArray_Dims newshape;
807
PyArray_ORDER fortran=PyArray_ANYORDER;
768
ref = PyDict_GetItemString(kwds, "refcheck");
770
refcheck = PyInt_AsLong(ref);
771
if (refcheck==-1 && PyErr_Occurred()) {
775
ref = PyDict_GetItemString(kwds, "order");
777
(PyArray_OrderConverter(ref, &fortran) == PY_FAIL))
780
n = PyTuple_Size(args);
782
if (PyTuple_GET_ITEM(args, 0) == Py_None) {
786
if (!PyArg_ParseTuple(args, "O&", PyArray_IntpConverter,
787
&newshape)) return NULL;
790
if (!PyArray_IntpConverter(args, &newshape)) {
791
if (!PyErr_Occurred()) {
792
PyErr_SetString(PyExc_TypeError,
798
ret = PyArray_Resize(self, &newshape, refcheck, fortran);
799
PyDimMem_FREE(newshape.ptr);
800
if (ret == NULL) return NULL;
811
ref = PyDict_GetItemString(kwds, "refcheck");
813
refcheck = PyInt_AsLong(ref);
814
if (refcheck==-1 && PyErr_Occurred()) {
818
ref = PyDict_GetItemString(kwds, "order");
820
(PyArray_OrderConverter(ref, &fortran) == PY_FAIL))
823
n = PyTuple_Size(args);
825
if (PyTuple_GET_ITEM(args, 0) == Py_None) {
829
if (!PyArg_ParseTuple(args, "O&", PyArray_IntpConverter,
830
&newshape)) return NULL;
833
if (!PyArray_IntpConverter(args, &newshape)) {
834
if (!PyErr_Occurred()) {
835
PyErr_SetString(PyExc_TypeError,
841
ret = PyArray_Resize(self, &newshape, refcheck, fortran);
842
PyDimMem_FREE(newshape.ptr);
843
if (ret == NULL) return NULL;
806
849
static PyObject *
807
850
array_repeat(PyArrayObject *self, PyObject *args, PyObject *kwds) {
810
static char *kwlist[] = {"repeats", "axis", NULL};
812
if (!PyArg_ParseTupleAndKeywords(args, kwds, "O|O&", kwlist,
813
&repeats, PyArray_AxisConverter,
816
return _ARET(PyArray_Repeat(self, repeats, axis));
853
static char *kwlist[] = {"repeats", "axis", NULL};
855
if (!PyArg_ParseTupleAndKeywords(args, kwds, "O|O&", kwlist,
856
&repeats, PyArray_AxisConverter,
859
return _ARET(PyArray_Repeat(self, repeats, axis));
819
862
static PyObject *
820
863
array_choose(PyArrayObject *self, PyObject *args, PyObject *kwds)
824
PyArrayObject *out=NULL;
825
NPY_CLIPMODE clipmode=NPY_RAISE;
827
n = PyTuple_Size(args);
829
if (!PyArg_ParseTuple(args, "O", &choices))
835
if (kwds && PyDict_Check(kwds)) {
836
if (PyArray_OutputConverter(PyDict_GetItemString(kwds,
840
if (PyArray_ClipmodeConverter(PyDict_GetItemString(kwds,
842
&clipmode) == PY_FAIL)
846
return _ARET(PyArray_Choose(self, choices, out, clipmode));
867
PyArrayObject *out=NULL;
868
NPY_CLIPMODE clipmode=NPY_RAISE;
870
n = PyTuple_Size(args);
872
if (!PyArg_ParseTuple(args, "O", &choices))
878
if (kwds && PyDict_Check(kwds)) {
879
if (PyArray_OutputConverter(PyDict_GetItemString(kwds,
883
if (PyArray_ClipmodeConverter(PyDict_GetItemString(kwds,
885
&clipmode) == PY_FAIL)
889
return _ARET(PyArray_Choose(self, choices, out, clipmode));
849
892
static PyObject *
850
893
array_sort(PyArrayObject *self, PyObject *args, PyObject *kwds)
854
PyArray_SORTKIND which=PyArray_QUICKSORT;
855
PyObject *order=NULL;
856
PyArray_Descr *saved=NULL;
858
static char *kwlist[] = {"axis", "kind", "order", NULL};
860
if (!PyArg_ParseTupleAndKeywords(args, kwds, "|iO&O", kwlist, &axis,
861
PyArray_SortkindConverter, &which,
865
if (order == Py_None) order = NULL;
869
if (saved->names == NULL) {
870
PyErr_SetString(PyExc_ValueError, "Cannot specify " \
871
"order when the array has no fields.");
874
new_name = PyObject_CallMethod(_numpy_internal, "_newnames",
876
if (new_name == NULL) return NULL;
877
newd = PyArray_DescrNew(saved);
878
newd->names = new_name;
882
val = PyArray_Sort(self, axis, which);
884
Py_XDECREF(self->descr);
887
if (val < 0) return NULL;
897
PyArray_SORTKIND which=PyArray_QUICKSORT;
898
PyObject *order=NULL;
899
PyArray_Descr *saved=NULL;
901
static char *kwlist[] = {"axis", "kind", "order", NULL};
903
if (!PyArg_ParseTupleAndKeywords(args, kwds, "|iO&O", kwlist, &axis,
904
PyArray_SortkindConverter, &which,
908
if (order == Py_None) order = NULL;
911
PyObject *_numpy_internal;
913
if (saved->names == NULL) {
914
PyErr_SetString(PyExc_ValueError, "Cannot specify " \
915
"order when the array has no fields.");
918
_numpy_internal = PyImport_ImportModule("numpy.core._internal");
919
if (_numpy_internal == NULL) return NULL;
920
new_name = PyObject_CallMethod(_numpy_internal, "_newnames",
922
Py_DECREF(_numpy_internal);
923
if (new_name == NULL) return NULL;
924
newd = PyArray_DescrNew(saved);
925
newd->names = new_name;
929
val = PyArray_Sort(self, axis, which);
931
Py_XDECREF(self->descr);
934
if (val < 0) return NULL;
892
939
static PyObject *
893
940
array_argsort(PyArrayObject *self, PyObject *args, PyObject *kwds)
896
PyArray_SORTKIND which=PyArray_QUICKSORT;
897
PyObject *order=NULL, *res;
898
PyArray_Descr *newd, *saved=NULL;
899
static char *kwlist[] = {"axis", "kind", "order", NULL};
901
if (!PyArg_ParseTupleAndKeywords(args, kwds, "|O&O&O", kwlist,
902
PyArray_AxisConverter, &axis,
903
PyArray_SortkindConverter, &which,
907
if (order == Py_None) order = NULL;
911
if (saved->names == NULL) {
912
PyErr_SetString(PyExc_ValueError, "Cannot specify " \
913
"order when the array has no fields.");
916
new_name = PyObject_CallMethod(_numpy_internal, "_newnames",
918
if (new_name == NULL) return NULL;
919
newd = PyArray_DescrNew(saved);
920
newd->names = new_name;
924
res = PyArray_ArgSort(self, axis, which);
926
Py_XDECREF(self->descr);
943
PyArray_SORTKIND which=PyArray_QUICKSORT;
944
PyObject *order=NULL, *res;
945
PyArray_Descr *newd, *saved=NULL;
946
static char *kwlist[] = {"axis", "kind", "order", NULL};
948
if (!PyArg_ParseTupleAndKeywords(args, kwds, "|O&O&O", kwlist,
949
PyArray_AxisConverter, &axis,
950
PyArray_SortkindConverter, &which,
954
if (order == Py_None) order = NULL;
957
PyObject *_numpy_internal;
959
if (saved->names == NULL) {
960
PyErr_SetString(PyExc_ValueError, "Cannot specify " \
961
"order when the array has no fields.");
964
_numpy_internal = PyImport_ImportModule("numpy.core._internal");
965
if (_numpy_internal == NULL) return NULL;
966
new_name = PyObject_CallMethod(_numpy_internal, "_newnames",
968
Py_DECREF(_numpy_internal);
969
if (new_name == NULL) return NULL;
970
newd = PyArray_DescrNew(saved);
971
newd->names = new_name;
975
res = PyArray_ArgSort(self, axis, which);
977
Py_XDECREF(self->descr);
932
983
static PyObject *
933
984
array_searchsorted(PyArrayObject *self, PyObject *args, PyObject *kwds)
935
static char *kwlist[] = {"keys", "side", NULL};
937
NPY_SEARCHSIDE side = NPY_SEARCHLEFT;
939
if (!PyArg_ParseTupleAndKeywords(args, kwds, "O|O&:searchsorted",
941
PyArray_SearchsideConverter, &side))
944
return _ARET(PyArray_SearchSorted(self, keys, side));
986
static char *kwlist[] = {"keys", "side", NULL};
988
NPY_SEARCHSIDE side = NPY_SEARCHLEFT;
990
if (!PyArg_ParseTupleAndKeywords(args, kwds, "O|O&:searchsorted",
992
PyArray_SearchsideConverter, &side))
995
return _ARET(PyArray_SearchSorted(self, keys, side));
948
999
_deepcopy_call(char *iptr, char *optr, PyArray_Descr *dtype,
949
PyObject *deepcopy, PyObject *visit)
1000
PyObject *deepcopy, PyObject *visit)
951
if (!PyDataType_REFCHK(dtype)) return;
952
else if (PyDescr_HASFIELDS(dtype)) {
953
PyObject *key, *value, *title=NULL;
957
while (PyDict_Next(dtype->fields, &pos, &key, &value)) {
958
if (!PyArg_ParseTuple(value, "Oi|O", &new, &offset,
960
_deepcopy_call(iptr + offset, optr + offset, new,
1002
if (!PyDataType_REFCHK(dtype)) return;
1003
else if (PyDescr_HASFIELDS(dtype)) {
1004
PyObject *key, *value, *title=NULL;
1008
while (PyDict_Next(dtype->fields, &pos, &key, &value)) {
1009
if (!PyArg_ParseTuple(value, "Oi|O", &new, &offset,
1011
_deepcopy_call(iptr + offset, optr + offset, new,
965
PyObject **itemp, **otemp;
967
itemp = (PyObject **)iptr;
968
otemp = (PyObject **)optr;
970
/* call deepcopy on this argument */
971
res = PyObject_CallFunctionObjArgs(deepcopy,
972
*itemp, visit, NULL);
1016
PyObject **itemp, **otemp;
1018
itemp = (PyObject **)iptr;
1019
otemp = (PyObject **)optr;
1021
/* call deepcopy on this argument */
1022
res = PyObject_CallFunctionObjArgs(deepcopy,
1023
*itemp, visit, NULL);
981
1032
static PyObject *
982
1033
array_deepcopy(PyArrayObject *self, PyObject *args)
986
PyArrayIterObject *it;
987
PyObject *copy, *ret, *deepcopy;
1037
PyArrayIterObject *it;
1038
PyObject *copy, *ret, *deepcopy;
989
if (!PyArg_ParseTuple(args, "O", &visit)) return NULL;
990
ret = PyArray_Copy(self);
991
if (PyDataType_REFCHK(self->descr)) {
992
copy = PyImport_ImportModule("copy");
993
if (copy == NULL) return NULL;
994
deepcopy = PyObject_GetAttrString(copy, "deepcopy");
996
if (deepcopy == NULL) return NULL;
997
it = (PyArrayIterObject *)PyArray_IterNew((PyObject *)self);
998
if (it == NULL) {Py_DECREF(deepcopy); return NULL;}
999
optr = PyArray_DATA(ret);
1000
while(it->index < it->size) {
1001
_deepcopy_call(it->dataptr, optr, self->descr,
1003
optr += self->descr->elsize;
1004
PyArray_ITER_NEXT(it);
1006
Py_DECREF(deepcopy);
1040
if (!PyArg_ParseTuple(args, "O", &visit)) return NULL;
1041
ret = PyArray_Copy(self);
1042
if (PyDataType_REFCHK(self->descr)) {
1043
copy = PyImport_ImportModule("copy");
1044
if (copy == NULL) return NULL;
1045
deepcopy = PyObject_GetAttrString(copy, "deepcopy");
1047
if (deepcopy == NULL) return NULL;
1048
it = (PyArrayIterObject *)PyArray_IterNew((PyObject *)self);
1049
if (it == NULL) {Py_DECREF(deepcopy); return NULL;}
1050
optr = PyArray_DATA(ret);
1051
while(it->index < it->size) {
1052
_deepcopy_call(it->dataptr, optr, self->descr,
1054
optr += self->descr->elsize;
1055
PyArray_ITER_NEXT(it);
1057
Py_DECREF(deepcopy);
1012
1063
/* Convert Array to flat list (using getitem) */
1013
1064
static PyObject *
1014
1065
_getlist_pkl(PyArrayObject *self)
1016
PyObject *theobject;
1017
PyArrayIterObject *iter=NULL;
1019
PyArray_GetItemFunc *getitem;
1067
PyObject *theobject;
1068
PyArrayIterObject *iter=NULL;
1070
PyArray_GetItemFunc *getitem;
1021
getitem = self->descr->f->getitem;
1022
iter = (PyArrayIterObject *)PyArray_IterNew((PyObject *)self);
1023
if (iter == NULL) return NULL;
1024
list = PyList_New(iter->size);
1025
if (list == NULL) {Py_DECREF(iter); return NULL;}
1026
while (iter->index < iter->size) {
1027
theobject = getitem(iter->dataptr, self);
1028
PyList_SET_ITEM(list, (int) iter->index, theobject);
1029
PyArray_ITER_NEXT(iter);
1072
getitem = self->descr->f->getitem;
1073
iter = (PyArrayIterObject *)PyArray_IterNew((PyObject *)self);
1074
if (iter == NULL) return NULL;
1075
list = PyList_New(iter->size);
1076
if (list == NULL) {Py_DECREF(iter); return NULL;}
1077
while (iter->index < iter->size) {
1078
theobject = getitem(iter->dataptr, self);
1079
PyList_SET_ITEM(list, (int) iter->index, theobject);
1080
PyArray_ITER_NEXT(iter);
1036
1087
_setlist_pkl(PyArrayObject *self, PyObject *list)
1038
PyObject *theobject;
1039
PyArrayIterObject *iter=NULL;
1040
PyArray_SetItemFunc *setitem;
1089
PyObject *theobject;
1090
PyArrayIterObject *iter=NULL;
1091
PyArray_SetItemFunc *setitem;
1042
setitem = self->descr->f->setitem;
1043
iter = (PyArrayIterObject *)PyArray_IterNew((PyObject *)self);
1044
if (iter == NULL) return -1;
1045
while(iter->index < iter->size) {
1046
theobject = PyList_GET_ITEM(list, (int) iter->index);
1047
setitem(theobject, iter->dataptr, self);
1048
PyArray_ITER_NEXT(iter);
1093
setitem = self->descr->f->setitem;
1094
iter = (PyArrayIterObject *)PyArray_IterNew((PyObject *)self);
1095
if (iter == NULL) return -1;
1096
while(iter->index < iter->size) {
1097
theobject = PyList_GET_ITEM(list, (int) iter->index);
1098
setitem(theobject, iter->dataptr, self);
1099
PyArray_ITER_NEXT(iter);
1055
1106
static PyObject *
1056
1107
array_reduce(PyArrayObject *self, PyObject *args)
1058
/* version number of this pickle type. Increment if we need to
1059
change the format. Be sure to handle the old versions in
1061
const int version = 1;
1062
PyObject *ret=NULL, *state=NULL, *obj=NULL, *mod=NULL;
1063
PyObject *mybool, *thestr=NULL;
1064
PyArray_Descr *descr;
1066
/* Return a tuple of (callable object, arguments, object's state) */
1067
/* We will put everything in the object's state, so that on UnPickle
1068
it can use the string object as memory without a copy */
1070
ret = PyTuple_New(3);
1071
if (ret == NULL) return NULL;
1072
mod = PyImport_ImportModule("numpy.core.multiarray");
1073
if (mod == NULL) {Py_DECREF(ret); return NULL;}
1074
obj = PyObject_GetAttrString(mod, "_reconstruct");
1076
PyTuple_SET_ITEM(ret, 0, obj);
1077
PyTuple_SET_ITEM(ret, 1,
1078
Py_BuildValue("ONc",
1079
(PyObject *)self->ob_type,
1080
Py_BuildValue("(N)",
1082
/* dummy data-type */
1085
/* Now fill in object's state. This is a tuple with
1088
1) an integer with the pickle version.
1089
2) a Tuple giving the shape
1090
3) a PyArray_Descr Object (with correct bytorder set)
1091
4) a Bool stating if Fortran or not
1092
5) a Python object representing the data (a string, or
1093
a list or any user-defined object).
1095
Notice because Python does not describe a mechanism to write
1096
raw data to the pickle, this performs a copy to a string first
1099
state = PyTuple_New(5);
1100
if (state == NULL) {
1101
Py_DECREF(ret); return NULL;
1103
PyTuple_SET_ITEM(state, 0, PyInt_FromLong(version));
1104
PyTuple_SET_ITEM(state, 1, PyObject_GetAttrString((PyObject *)self,
1106
descr = self->descr;
1108
PyTuple_SET_ITEM(state, 2, (PyObject *)descr);
1109
mybool = (PyArray_ISFORTRAN(self) ? Py_True : Py_False);
1111
PyTuple_SET_ITEM(state, 3, mybool);
1112
if (PyDataType_FLAGCHK(self->descr, NPY_LIST_PICKLE)) {
1113
thestr = _getlist_pkl(self);
1116
thestr = PyArray_ToString(self, NPY_ANYORDER);
1118
if (thestr == NULL) {
1123
PyTuple_SET_ITEM(state, 4, thestr);
1124
PyTuple_SET_ITEM(ret, 2, state);
1109
/* version number of this pickle type. Increment if we need to
1110
change the format. Be sure to handle the old versions in
1112
const int version = 1;
1113
PyObject *ret=NULL, *state=NULL, *obj=NULL, *mod=NULL;
1114
PyObject *mybool, *thestr=NULL;
1115
PyArray_Descr *descr;
1117
/* Return a tuple of (callable object, arguments, object's state) */
1118
/* We will put everything in the object's state, so that on UnPickle
1119
it can use the string object as memory without a copy */
1121
ret = PyTuple_New(3);
1122
if (ret == NULL) return NULL;
1123
mod = PyImport_ImportModule("numpy.core.multiarray");
1124
if (mod == NULL) {Py_DECREF(ret); return NULL;}
1125
obj = PyObject_GetAttrString(mod, "_reconstruct");
1127
PyTuple_SET_ITEM(ret, 0, obj);
1128
PyTuple_SET_ITEM(ret, 1,
1129
Py_BuildValue("ONc",
1130
(PyObject *)self->ob_type,
1131
Py_BuildValue("(N)",
1133
/* dummy data-type */
1136
/* Now fill in object's state. This is a tuple with
1139
1) an integer with the pickle version.
1140
2) a Tuple giving the shape
1141
3) a PyArray_Descr Object (with correct bytorder set)
1142
4) a Bool stating if Fortran or not
1143
5) a Python object representing the data (a string, or
1144
a list or any user-defined object).
1146
Notice because Python does not describe a mechanism to write
1147
raw data to the pickle, this performs a copy to a string first
1150
state = PyTuple_New(5);
1151
if (state == NULL) {
1152
Py_DECREF(ret); return NULL;
1154
PyTuple_SET_ITEM(state, 0, PyInt_FromLong(version));
1155
PyTuple_SET_ITEM(state, 1, PyObject_GetAttrString((PyObject *)self,
1157
descr = self->descr;
1159
PyTuple_SET_ITEM(state, 2, (PyObject *)descr);
1160
mybool = (PyArray_ISFORTRAN(self) ? Py_True : Py_False);
1162
PyTuple_SET_ITEM(state, 3, mybool);
1163
if (PyDataType_FLAGCHK(self->descr, NPY_LIST_PICKLE)) {
1164
thestr = _getlist_pkl(self);
1167
thestr = PyArray_ToString(self, NPY_ANYORDER);
1169
if (thestr == NULL) {
1174
PyTuple_SET_ITEM(state, 4, thestr);
1175
PyTuple_SET_ITEM(ret, 2, state);
1136
1187
static PyObject *
1137
1188
array_setstate(PyArrayObject *self, PyObject *args)
1140
PyArray_Descr *typecode;
1146
intp size, dimensions[MAX_DIMS];
1149
/* This will free any memory associated with a and
1150
use the string in setstate as the (writeable) memory.
1152
if (!PyArg_ParseTuple(args, "(iO!O!iO)", &version, &PyTuple_Type,
1153
&shape, &PyArrayDescr_Type, &typecode,
1154
&fortran, &rawdata)) {
1157
if (!PyArg_ParseTuple(args, "(O!O!iO)", &PyTuple_Type,
1158
&shape, &PyArrayDescr_Type, &typecode,
1159
&fortran, &rawdata)) {
1164
/* If we ever need another pickle format, increment the version
1165
number. But we should still be able to handle the old versions.
1166
We've only got one right now. */
1167
if (version != 1 && version != 0) {
1168
PyErr_Format(PyExc_ValueError,
1169
"can't handle version %d of numpy.ndarray pickle",
1174
Py_XDECREF(self->descr);
1175
self->descr = typecode;
1176
Py_INCREF(typecode);
1177
nd = PyArray_IntpFromSequence(shape, dimensions, MAX_DIMS);
1178
if (nd < 0) return NULL;
1179
size = PyArray_MultiplyList(dimensions, nd);
1180
if (self->descr->elsize == 0) {
1181
PyErr_SetString(PyExc_ValueError, "Invalid data-type size.");
1184
if (size < 0 || size > MAX_INTP / self->descr->elsize) {
1189
if (PyDataType_FLAGCHK(typecode, NPY_LIST_PICKLE)) {
1190
if (!PyList_Check(rawdata)) {
1191
PyErr_SetString(PyExc_TypeError,
1192
"object pickle not returning list");
1197
if (!PyString_Check(rawdata)) {
1198
PyErr_SetString(PyExc_TypeError,
1199
"pickle not returning string");
1203
if (PyString_AsStringAndSize(rawdata, &datastr, &len))
1206
if ((len != (self->descr->elsize * size))) {
1207
PyErr_SetString(PyExc_ValueError,
1208
"buffer size does not" \
1209
" match array size");
1214
if ((self->flags & OWNDATA)) {
1215
if (self->data != NULL)
1216
PyDataMem_FREE(self->data);
1217
self->flags &= ~OWNDATA;
1219
Py_XDECREF(self->base);
1221
self->flags &= ~UPDATEIFCOPY;
1223
if (self->dimensions != NULL) {
1191
PyArray_Descr *typecode;
1197
intp size, dimensions[MAX_DIMS];
1200
/* This will free any memory associated with a and
1201
use the string in setstate as the (writeable) memory.
1203
if (!PyArg_ParseTuple(args, "(iO!O!iO)", &version, &PyTuple_Type,
1204
&shape, &PyArrayDescr_Type, &typecode,
1205
&fortran, &rawdata)) {
1208
if (!PyArg_ParseTuple(args, "(O!O!iO)", &PyTuple_Type,
1209
&shape, &PyArrayDescr_Type, &typecode,
1210
&fortran, &rawdata)) {
1215
/* If we ever need another pickle format, increment the version
1216
number. But we should still be able to handle the old versions.
1217
We've only got one right now. */
1218
if (version != 1 && version != 0) {
1219
PyErr_Format(PyExc_ValueError,
1220
"can't handle version %d of numpy.ndarray pickle",
1225
Py_XDECREF(self->descr);
1226
self->descr = typecode;
1227
Py_INCREF(typecode);
1228
nd = PyArray_IntpFromSequence(shape, dimensions, MAX_DIMS);
1229
if (nd < 0) return NULL;
1230
size = PyArray_MultiplyList(dimensions, nd);
1231
if (self->descr->elsize == 0) {
1232
PyErr_SetString(PyExc_ValueError, "Invalid data-type size.");
1235
if (size < 0 || size > MAX_INTP / self->descr->elsize) {
1240
if (PyDataType_FLAGCHK(typecode, NPY_LIST_PICKLE)) {
1241
if (!PyList_Check(rawdata)) {
1242
PyErr_SetString(PyExc_TypeError,
1243
"object pickle not returning list");
1248
if (!PyString_Check(rawdata)) {
1249
PyErr_SetString(PyExc_TypeError,
1250
"pickle not returning string");
1254
if (PyString_AsStringAndSize(rawdata, &datastr, &len))
1257
if ((len != (self->descr->elsize * size))) {
1258
PyErr_SetString(PyExc_ValueError,
1259
"buffer size does not" \
1260
" match array size");
1265
if ((self->flags & OWNDATA)) {
1266
if (self->data != NULL)
1267
PyDataMem_FREE(self->data);
1268
self->flags &= ~OWNDATA;
1270
Py_XDECREF(self->base);
1272
self->flags &= ~UPDATEIFCOPY;
1274
if (self->dimensions != NULL) {
1275
PyDimMem_FREE(self->dimensions);
1276
self->dimensions = NULL;
1279
self->flags = DEFAULT;
1284
self->dimensions = PyDimMem_NEW(nd * 2);
1285
self->strides = self->dimensions + nd;
1286
memcpy(self->dimensions, dimensions, sizeof(intp)*nd);
1287
(void) _array_fill_strides(self->strides, dimensions, nd,
1288
(size_t) self->descr->elsize,
1289
(fortran ? FORTRAN : CONTIGUOUS),
1293
if (!PyDataType_FLAGCHK(typecode, NPY_LIST_PICKLE)) {
1294
int swap=!PyArray_ISNOTSWAPPED(self);
1295
self->data = datastr;
1296
if (!_IsAligned(self) || swap) {
1297
intp num = PyArray_NBYTES(self);
1298
self->data = PyDataMem_NEW(num);
1299
if (self->data == NULL) {
1224
1301
PyDimMem_FREE(self->dimensions);
1225
self->dimensions = NULL;
1228
self->flags = DEFAULT;
1233
self->dimensions = PyDimMem_NEW(nd * 2);
1234
self->strides = self->dimensions + nd;
1235
memcpy(self->dimensions, dimensions, sizeof(intp)*nd);
1236
(void) _array_fill_strides(self->strides, dimensions, nd,
1237
(size_t) self->descr->elsize,
1238
(fortran ? FORTRAN : CONTIGUOUS),
1242
if (!PyDataType_FLAGCHK(typecode, NPY_LIST_PICKLE)) {
1243
int swap=!PyArray_ISNOTSWAPPED(self);
1244
self->data = datastr;
1245
if (!_IsAligned(self) || swap) {
1246
intp num = PyArray_NBYTES(self);
1247
self->data = PyDataMem_NEW(num);
1248
if (self->data == NULL) {
1250
PyDimMem_FREE(self->dimensions);
1251
return PyErr_NoMemory();
1253
if (swap) { /* byte-swap on pickle-read */
1254
intp numels = num / self->descr->elsize;
1255
self->descr->f->copyswapn(self->data, self->descr->elsize,
1256
datastr, self->descr->elsize,
1258
if (!PyArray_ISEXTENDED(self)) {
1259
self->descr = PyArray_DescrFromType(self->descr->type_num);
1262
self->descr = PyArray_DescrNew(typecode);
1263
if (self->descr->byteorder == PyArray_BIG)
1264
self->descr->byteorder = PyArray_LITTLE;
1265
else if (self->descr->byteorder == PyArray_LITTLE)
1266
self->descr->byteorder = PyArray_BIG;
1268
Py_DECREF(typecode);
1271
memcpy(self->data, datastr, num);
1273
self->flags |= OWNDATA;
1277
self->base = rawdata;
1278
Py_INCREF(self->base);
1282
self->data = PyDataMem_NEW(PyArray_NBYTES(self));
1283
if (self->data == NULL) {
1285
self->data = PyDataMem_NEW(self->descr->elsize);
1286
if (self->dimensions) PyDimMem_FREE(self->dimensions);
1287
return PyErr_NoMemory();
1289
if (PyDataType_FLAGCHK(self->descr, NPY_NEEDS_INIT))
1290
memset(self->data, 0, PyArray_NBYTES(self));
1291
self->flags |= OWNDATA;
1293
if (_setlist_pkl(self, rawdata) < 0)
1297
PyArray_UpdateFlags(self, UPDATE_ALL);
1302
return PyErr_NoMemory();
1304
if (swap) { /* byte-swap on pickle-read */
1305
intp numels = num / self->descr->elsize;
1306
self->descr->f->copyswapn(self->data, self->descr->elsize,
1307
datastr, self->descr->elsize,
1309
if (!PyArray_ISEXTENDED(self)) {
1310
self->descr = PyArray_DescrFromType(self->descr->type_num);
1313
self->descr = PyArray_DescrNew(typecode);
1314
if (self->descr->byteorder == PyArray_BIG)
1315
self->descr->byteorder = PyArray_LITTLE;
1316
else if (self->descr->byteorder == PyArray_LITTLE)
1317
self->descr->byteorder = PyArray_BIG;
1319
Py_DECREF(typecode);
1322
memcpy(self->data, datastr, num);
1324
self->flags |= OWNDATA;
1328
self->base = rawdata;
1329
Py_INCREF(self->base);
1333
self->data = PyDataMem_NEW(PyArray_NBYTES(self));
1334
if (self->data == NULL) {
1336
self->data = PyDataMem_NEW(self->descr->elsize);
1337
if (self->dimensions) PyDimMem_FREE(self->dimensions);
1338
return PyErr_NoMemory();
1340
if (PyDataType_FLAGCHK(self->descr, NPY_NEEDS_INIT))
1341
memset(self->data, 0, PyArray_NBYTES(self));
1342
self->flags |= OWNDATA;
1344
if (_setlist_pkl(self, rawdata) < 0)
1348
PyArray_UpdateFlags(self, UPDATE_ALL);
1305
1356
PyArray_Dump(PyObject *self, PyObject *file, int protocol)
1307
PyObject *cpick=NULL;
1309
if (protocol < 0) protocol = 2;
1311
cpick = PyImport_ImportModule("cPickle");
1312
if (cpick==NULL) return -1;
1314
if PyString_Check(file) {
1315
file = PyFile_FromString(PyString_AS_STRING(file), "wb");
1316
if (file==NULL) return -1;
1318
else Py_INCREF(file);
1319
ret = PyObject_CallMethod(cpick, "dump", "OOi", self,
1324
if (PyErr_Occurred()) return -1;
1358
PyObject *cpick=NULL;
1360
if (protocol < 0) protocol = 2;
1362
cpick = PyImport_ImportModule("cPickle");
1363
if (cpick==NULL) return -1;
1365
if PyString_Check(file) {
1366
file = PyFile_FromString(PyString_AS_STRING(file), "wb");
1367
if (file==NULL) return -1;
1369
else Py_INCREF(file);
1370
ret = PyObject_CallMethod(cpick, "dump", "OOi", self,
1375
if (PyErr_Occurred()) return -1;
1329
1380
static PyObject *
1330
1381
PyArray_Dumps(PyObject *self, int protocol)
1332
PyObject *cpick=NULL;
1334
if (protocol < 0) protocol = 2;
1383
PyObject *cpick=NULL;
1385
if (protocol < 0) protocol = 2;
1336
cpick = PyImport_ImportModule("cPickle");
1337
if (cpick==NULL) return NULL;
1338
ret = PyObject_CallMethod(cpick, "dumps", "Oi", self, protocol);
1387
cpick = PyImport_ImportModule("cPickle");
1388
if (cpick==NULL) return NULL;
1389
ret = PyObject_CallMethod(cpick, "dumps", "Oi", self, protocol);
1344
1395
static PyObject *
1345
1396
array_dump(PyArrayObject *self, PyObject *args)
1347
PyObject *file=NULL;
1398
PyObject *file=NULL;
1350
if (!PyArg_ParseTuple(args, "O", &file))
1352
ret = PyArray_Dump((PyObject *)self, file, 2);
1353
if (ret < 0) return NULL;
1401
if (!PyArg_ParseTuple(args, "O", &file))
1403
ret = PyArray_Dump((PyObject *)self, file, 2);
1404
if (ret < 0) return NULL;
1359
1410
static PyObject *
1360
1411
array_dumps(PyArrayObject *self, PyObject *args)
1362
if (!PyArg_ParseTuple(args, ""))
1364
return PyArray_Dumps((PyObject *)self, 2);
1413
if (!PyArg_ParseTuple(args, ""))
1415
return PyArray_Dumps((PyObject *)self, 2);
1368
1419
static PyObject *
1369
1420
array_transpose(PyArrayObject *self, PyObject *args)
1371
PyObject *shape=Py_None;
1373
PyArray_Dims permute;
1376
n = PyTuple_Size(args);
1377
if (n > 1) shape = args;
1378
else if (n == 1) shape = PyTuple_GET_ITEM(args, 0);
1380
if (shape == Py_None)
1381
ret = PyArray_Transpose(self, NULL);
1383
if (!PyArray_IntpConverter(shape, &permute)) return NULL;
1384
ret = PyArray_Transpose(self, &permute);
1385
PyDimMem_FREE(permute.ptr);
1422
PyObject *shape=Py_None;
1424
PyArray_Dims permute;
1427
n = PyTuple_Size(args);
1428
if (n > 1) shape = args;
1429
else if (n == 1) shape = PyTuple_GET_ITEM(args, 0);
1431
if (shape == Py_None)
1432
ret = PyArray_Transpose(self, NULL);
1434
if (!PyArray_IntpConverter(shape, &permute)) return NULL;
1435
ret = PyArray_Transpose(self, &permute);
1436
PyDimMem_FREE(permute.ptr);
1391
/* Return typenumber from dtype2 unless it is NULL, then return
1442
/* Return typenumber from dtype2 unless it is NULL, then return
1392
1443
NPY_DOUBLE if dtype1->type_num is integer or bool
1393
and dtype1->type_num otherwise.
1444
and dtype1->type_num otherwise.
1396
1447
_get_type_num_double(PyArray_Descr *dtype1, PyArray_Descr *dtype2)
1399
return dtype2->type_num;
1401
/* For integer or bool data-types */
1402
if (dtype1->type_num < NPY_FLOAT) {
1406
return dtype1->type_num;
1450
return dtype2->type_num;
1452
/* For integer or bool data-types */
1453
if (dtype1->type_num < NPY_FLOAT) {
1457
return dtype1->type_num;
1410
1461
#define _CHKTYPENUM(typ) ((typ) ? (typ)->type_num : PyArray_NOTYPE)
1412
1463
static PyObject *
1413
1464
array_mean(PyArrayObject *self, PyObject *args, PyObject *kwds)
1416
PyArray_Descr *dtype=NULL;
1417
PyArrayObject *out=NULL;
1419
static char *kwlist[] = {"axis", "dtype", "out", NULL};
1421
if (!PyArg_ParseTupleAndKeywords(args, kwds, "|O&O&O&", kwlist,
1422
PyArray_AxisConverter,
1423
&axis, PyArray_DescrConverter2,
1425
PyArray_OutputConverter,
1428
num = _get_type_num_double(self->descr, dtype);
1429
return PyArray_Mean(self, axis, num, out);
1467
PyArray_Descr *dtype=NULL;
1468
PyArrayObject *out=NULL;
1470
static char *kwlist[] = {"axis", "dtype", "out", NULL};
1472
if (!PyArg_ParseTupleAndKeywords(args, kwds, "|O&O&O&", kwlist,
1473
PyArray_AxisConverter,
1474
&axis, PyArray_DescrConverter2,
1476
PyArray_OutputConverter,
1482
num = _get_type_num_double(self->descr, dtype);
1484
return PyArray_Mean(self, axis, num, out);
1432
1487
static PyObject *
1433
1488
array_sum(PyArrayObject *self, PyObject *args, PyObject *kwds)
1436
PyArray_Descr *dtype=NULL;
1437
PyArrayObject *out=NULL;
1438
static char *kwlist[] = {"axis", "dtype", "out", NULL};
1440
if (!PyArg_ParseTupleAndKeywords(args, kwds, "|O&O&O&", kwlist,
1441
PyArray_AxisConverter,
1442
&axis, PyArray_DescrConverter2,
1444
PyArray_OutputConverter,
1447
return PyArray_Sum(self, axis, _CHKTYPENUM(dtype), out);
1491
PyArray_Descr *dtype=NULL;
1492
PyArrayObject *out=NULL;
1494
static char *kwlist[] = {"axis", "dtype", "out", NULL};
1496
if (!PyArg_ParseTupleAndKeywords(args, kwds, "|O&O&O&", kwlist,
1497
PyArray_AxisConverter,
1498
&axis, PyArray_DescrConverter2,
1500
PyArray_OutputConverter,
1506
rtype = _CHKTYPENUM(dtype);
1508
return PyArray_Sum(self, axis, rtype, out);
1451
1512
static PyObject *
1452
1513
array_cumsum(PyArrayObject *self, PyObject *args, PyObject *kwds)
1455
PyArray_Descr *dtype=NULL;
1456
PyArrayObject *out=NULL;
1457
static char *kwlist[] = {"axis", "dtype", "out", NULL};
1459
if (!PyArg_ParseTupleAndKeywords(args, kwds, "|O&O&O&", kwlist,
1460
PyArray_AxisConverter,
1461
&axis, PyArray_DescrConverter2,
1463
PyArray_OutputConverter,
1466
return PyArray_CumSum(self, axis, _CHKTYPENUM(dtype), out);
1516
PyArray_Descr *dtype=NULL;
1517
PyArrayObject *out=NULL;
1519
static char *kwlist[] = {"axis", "dtype", "out", NULL};
1521
if (!PyArg_ParseTupleAndKeywords(args, kwds, "|O&O&O&", kwlist,
1522
PyArray_AxisConverter,
1523
&axis, PyArray_DescrConverter2,
1525
PyArray_OutputConverter,
1531
rtype = _CHKTYPENUM(dtype);
1533
return PyArray_CumSum(self, axis, rtype, out);
1469
1536
static PyObject *
1470
1537
array_prod(PyArrayObject *self, PyObject *args, PyObject *kwds)
1473
PyArray_Descr *dtype=NULL;
1474
PyArrayObject *out=NULL;
1475
static char *kwlist[] = {"axis", "dtype", "out", NULL};
1477
if (!PyArg_ParseTupleAndKeywords(args, kwds, "|O&O&O&", kwlist,
1478
PyArray_AxisConverter,
1479
&axis, PyArray_DescrConverter2,
1481
PyArray_OutputConverter,
1484
return PyArray_Prod(self, axis, _CHKTYPENUM(dtype), out);
1540
PyArray_Descr *dtype=NULL;
1541
PyArrayObject *out=NULL;
1543
static char *kwlist[] = {"axis", "dtype", "out", NULL};
1545
if (!PyArg_ParseTupleAndKeywords(args, kwds, "|O&O&O&", kwlist,
1546
PyArray_AxisConverter,
1547
&axis, PyArray_DescrConverter2,
1549
PyArray_OutputConverter,
1555
rtype = _CHKTYPENUM(dtype);
1557
return PyArray_Prod(self, axis, rtype, out);
1487
1560
static PyObject *
1488
1561
array_cumprod(PyArrayObject *self, PyObject *args, PyObject *kwds)
1491
PyArray_Descr *dtype=NULL;
1492
PyArrayObject *out=NULL;
1493
static char *kwlist[] = {"axis", "dtype", "out", NULL};
1495
if (!PyArg_ParseTupleAndKeywords(args, kwds, "|O&O&O&", kwlist,
1496
PyArray_AxisConverter,
1497
&axis, PyArray_DescrConverter2,
1499
PyArray_OutputConverter,
1502
return PyArray_CumProd(self, axis, _CHKTYPENUM(dtype), out);
1564
PyArray_Descr *dtype=NULL;
1565
PyArrayObject *out=NULL;
1567
static char *kwlist[] = {"axis", "dtype", "out", NULL};
1569
if (!PyArg_ParseTupleAndKeywords(args, kwds, "|O&O&O&", kwlist,
1570
PyArray_AxisConverter,
1571
&axis, PyArray_DescrConverter2,
1573
PyArray_OutputConverter,
1579
rtype = _CHKTYPENUM(dtype);
1581
return PyArray_CumProd(self, axis, rtype, out);
1506
1585
static PyObject *
1507
1586
array_any(PyArrayObject *self, PyObject *args, PyObject *kwds)
1510
PyArrayObject *out=NULL;
1511
static char *kwlist[] = {"axis", "out", NULL};
1513
if (!PyArg_ParseTupleAndKeywords(args, kwds, "|O&O&", kwlist,
1514
PyArray_AxisConverter,
1516
PyArray_OutputConverter,
1520
return PyArray_Any(self, axis, out);
1589
PyArrayObject *out=NULL;
1590
static char *kwlist[] = {"axis", "out", NULL};
1592
if (!PyArg_ParseTupleAndKeywords(args, kwds, "|O&O&", kwlist,
1593
PyArray_AxisConverter,
1595
PyArray_OutputConverter,
1599
return PyArray_Any(self, axis, out);
1524
1603
static PyObject *
1525
1604
array_all(PyArrayObject *self, PyObject *args, PyObject *kwds)
1528
PyArrayObject *out=NULL;
1529
static char *kwlist[] = {"axis", "out", NULL};
1531
if (!PyArg_ParseTupleAndKeywords(args, kwds, "|O&O&", kwlist,
1532
PyArray_AxisConverter,
1534
PyArray_OutputConverter,
1538
return PyArray_All(self, axis, out);
1607
PyArrayObject *out=NULL;
1608
static char *kwlist[] = {"axis", "out", NULL};
1610
if (!PyArg_ParseTupleAndKeywords(args, kwds, "|O&O&", kwlist,
1611
PyArray_AxisConverter,
1613
PyArray_OutputConverter,
1617
return PyArray_All(self, axis, out);
1542
1621
static PyObject *
1622
__New_PyArray_Std(PyArrayObject *self, int axis, int rtype, PyArrayObject *out,
1623
int variance, int num);
1543
1625
array_stddev(PyArrayObject *self, PyObject *args, PyObject *kwds)
1546
PyArray_Descr *dtype=NULL;
1547
PyArrayObject *out=NULL;
1549
static char *kwlist[] = {"axis", "dtype", "out", NULL};
1551
if (!PyArg_ParseTupleAndKeywords(args, kwds, "|O&O&O&", kwlist,
1552
PyArray_AxisConverter,
1553
&axis, PyArray_DescrConverter2,
1555
PyArray_OutputConverter,
1558
num = _get_type_num_double(self->descr, dtype);
1559
return PyArray_Std(self, axis, num, out, 0);
1628
PyArray_Descr *dtype=NULL;
1629
PyArrayObject *out=NULL;
1632
static char *kwlist[] = {"axis", "dtype", "out", "ddof", NULL};
1634
if (!PyArg_ParseTupleAndKeywords(args, kwds, "|O&O&O&i", kwlist,
1635
PyArray_AxisConverter,
1636
&axis, PyArray_DescrConverter2,
1638
PyArray_OutputConverter,
1644
num = _get_type_num_double(self->descr, dtype);
1646
return __New_PyArray_Std(self, axis, num, out, 0, ddof);
1563
1650
static PyObject *
1564
1651
array_variance(PyArrayObject *self, PyObject *args, PyObject *kwds)
1567
PyArray_Descr *dtype=NULL;
1568
PyArrayObject *out=NULL;
1570
static char *kwlist[] = {"axis", "dtype", "out", NULL};
1572
if (!PyArg_ParseTupleAndKeywords(args, kwds, "|O&O&O&", kwlist,
1573
PyArray_AxisConverter,
1574
&axis, PyArray_DescrConverter2,
1576
PyArray_OutputConverter,
1579
num = _get_type_num_double(self->descr, dtype);
1580
return PyArray_Std(self, axis, num, out, 1);
1654
PyArray_Descr *dtype=NULL;
1655
PyArrayObject *out=NULL;
1658
static char *kwlist[] = {"axis", "dtype", "out", "ddof", NULL};
1660
if (!PyArg_ParseTupleAndKeywords(args, kwds, "|O&O&O&i", kwlist,
1661
PyArray_AxisConverter,
1662
&axis, PyArray_DescrConverter2,
1664
PyArray_OutputConverter,
1670
num = _get_type_num_double(self->descr, dtype);
1672
return __New_PyArray_Std(self, axis, num, out, 1, ddof);
1584
1676
static PyObject *
1585
1677
array_compress(PyArrayObject *self, PyObject *args, PyObject *kwds)
1588
PyObject *condition;
1589
PyArrayObject *out=NULL;
1590
static char *kwlist[] = {"condition", "axis", "out", NULL};
1592
if (!PyArg_ParseTupleAndKeywords(args, kwds, "O|O&O&", kwlist,
1593
&condition, PyArray_AxisConverter,
1595
PyArray_OutputConverter,
1598
return _ARET(PyArray_Compress(self, condition, axis, out));
1680
PyObject *condition;
1681
PyArrayObject *out=NULL;
1682
static char *kwlist[] = {"condition", "axis", "out", NULL};
1684
if (!PyArg_ParseTupleAndKeywords(args, kwds, "O|O&O&", kwlist,
1685
&condition, PyArray_AxisConverter,
1687
PyArray_OutputConverter,
1690
return _ARET(PyArray_Compress(self, condition, axis, out));
1602
1694
static PyObject *
1603
1695
array_nonzero(PyArrayObject *self, PyObject *args)
1605
if (!PyArg_ParseTuple(args, "")) return NULL;
1697
if (!PyArg_ParseTuple(args, "")) return NULL;
1607
return PyArray_Nonzero(self);
1699
return PyArray_Nonzero(self);
1611
1703
static PyObject *
1612
1704
array_trace(PyArrayObject *self, PyObject *args, PyObject *kwds)
1614
int axis1=0, axis2=1, offset=0;
1615
PyArray_Descr *dtype=NULL;
1616
PyArrayObject *out=NULL;
1617
static char *kwlist[] = {"offset", "axis1", "axis2", "dtype", "out", NULL};
1619
if (!PyArg_ParseTupleAndKeywords(args, kwds, "|iiiO&O&", kwlist,
1620
&offset, &axis1, &axis2,
1621
PyArray_DescrConverter2, &dtype,
1622
PyArray_OutputConverter, &out))
1625
return _ARET(PyArray_Trace(self, offset, axis1, axis2,
1626
_CHKTYPENUM(dtype), out));
1706
int axis1=0, axis2=1, offset=0;
1707
PyArray_Descr *dtype=NULL;
1708
PyArrayObject *out=NULL;
1710
static char *kwlist[] = {"offset", "axis1", "axis2", "dtype", "out", NULL};
1712
if (!PyArg_ParseTupleAndKeywords(args, kwds, "|iiiO&O&", kwlist,
1713
&offset, &axis1, &axis2,
1714
PyArray_DescrConverter2, &dtype,
1715
PyArray_OutputConverter, &out)) {
1720
rtype = _CHKTYPENUM(dtype);
1723
return _ARET(PyArray_Trace(self, offset, axis1, axis2,
1629
1727
#undef _CHKTYPENUM
1720
1822
static PyObject *
1721
1823
array_setflags(PyArrayObject *self, PyObject *args, PyObject *kwds)
1723
static char *kwlist[] = {"write", "align", "uic", NULL};
1724
PyObject *write=Py_None;
1725
PyObject *align=Py_None;
1726
PyObject *uic=Py_None;
1727
int flagback = self->flags;
1729
if (!PyArg_ParseTupleAndKeywords(args, kwds, "|OOO", kwlist,
1730
&write, &align, &uic))
1733
if (align != Py_None) {
1734
if (PyObject_Not(align)) self->flags &= ~ALIGNED;
1735
else if (_IsAligned(self)) self->flags |= ALIGNED;
1737
PyErr_SetString(PyExc_ValueError,
1738
"cannot set aligned flag of mis-"\
1739
"aligned array to True");
1744
if (uic != Py_None) {
1745
if (PyObject_IsTrue(uic)) {
1746
self->flags = flagback;
1747
PyErr_SetString(PyExc_ValueError,
1748
"cannot set UPDATEIFCOPY " \
1753
self->flags &= ~UPDATEIFCOPY;
1754
Py_XDECREF(self->base);
1759
if (write != Py_None) {
1760
if (PyObject_IsTrue(write))
1761
if (_IsWriteable(self)) {
1762
self->flags |= WRITEABLE;
1765
self->flags = flagback;
1766
PyErr_SetString(PyExc_ValueError,
1767
"cannot set WRITEABLE " \
1768
"flag to True of this " \
1773
self->flags &= ~WRITEABLE;
1825
static char *kwlist[] = {"write", "align", "uic", NULL};
1826
PyObject *write=Py_None;
1827
PyObject *align=Py_None;
1828
PyObject *uic=Py_None;
1829
int flagback = self->flags;
1831
if (!PyArg_ParseTupleAndKeywords(args, kwds, "|OOO", kwlist,
1832
&write, &align, &uic))
1835
if (align != Py_None) {
1836
if (PyObject_Not(align)) self->flags &= ~ALIGNED;
1837
else if (_IsAligned(self)) self->flags |= ALIGNED;
1839
PyErr_SetString(PyExc_ValueError,
1840
"cannot set aligned flag of mis-"\
1841
"aligned array to True");
1846
if (uic != Py_None) {
1847
if (PyObject_IsTrue(uic)) {
1848
self->flags = flagback;
1849
PyErr_SetString(PyExc_ValueError,
1850
"cannot set UPDATEIFCOPY " \
1855
self->flags &= ~UPDATEIFCOPY;
1856
Py_XDECREF(self->base);
1861
if (write != Py_None) {
1862
if (PyObject_IsTrue(write))
1863
if (_IsWriteable(self)) {
1864
self->flags |= WRITEABLE;
1867
self->flags = flagback;
1868
PyErr_SetString(PyExc_ValueError,
1869
"cannot set WRITEABLE " \
1870
"flag to True of this " \
1875
self->flags &= ~WRITEABLE;
1781
1883
static PyObject *
1782
1884
array_newbyteorder(PyArrayObject *self, PyObject *args)
1784
char endian = PyArray_SWAP;
1787
if (!PyArg_ParseTuple(args, "|O&", PyArray_ByteorderConverter,
1788
&endian)) return NULL;
1790
new = PyArray_DescrNewByteorder(self->descr, endian);
1791
if (!new) return NULL;
1792
return PyArray_View(self, new, NULL);
1886
char endian = PyArray_SWAP;
1889
if (!PyArg_ParseTuple(args, "|O&", PyArray_ByteorderConverter,
1890
&endian)) return NULL;
1892
new = PyArray_DescrNewByteorder(self->descr, endian);
1893
if (!new) return NULL;
1894
return PyArray_View(self, new, NULL);
1796
1898
static PyMethodDef array_methods[] = {
1799
{"__array__", (PyCFunction)array_getarray,
1800
METH_VARARGS, NULL},
1801
{"__array_wrap__", (PyCFunction)array_wraparray,
1802
METH_VARARGS, NULL},
1804
/* for the copy module */
1805
{"__copy__", (PyCFunction)array_copy,
1806
METH_VARARGS, NULL},
1807
{"__deepcopy__", (PyCFunction)array_deepcopy,
1808
METH_VARARGS, NULL},
1811
{"__reduce__", (PyCFunction) array_reduce,
1812
METH_VARARGS, NULL},
1813
{"__setstate__", (PyCFunction) array_setstate,
1814
METH_VARARGS, NULL},
1815
{"dumps", (PyCFunction) array_dumps,
1816
METH_VARARGS, NULL},
1817
{"dump", (PyCFunction) array_dump,
1818
METH_VARARGS, NULL},
1820
/* Original and Extended methods added 2005 */
1821
{"all", (PyCFunction)array_all,
1822
METH_VARARGS | METH_KEYWORDS, NULL},
1823
{"any", (PyCFunction)array_any,
1824
METH_VARARGS | METH_KEYWORDS, NULL},
1825
{"argmax", (PyCFunction)array_argmax,
1826
METH_VARARGS | METH_KEYWORDS, NULL},
1827
{"argmin", (PyCFunction)array_argmin,
1828
METH_VARARGS | METH_KEYWORDS, NULL},
1829
{"argsort", (PyCFunction)array_argsort,
1830
METH_VARARGS | METH_KEYWORDS, NULL},
1831
{"astype", (PyCFunction)array_cast,
1832
METH_VARARGS, NULL},
1833
{"byteswap", (PyCFunction)array_byteswap,
1834
METH_VARARGS, NULL},
1835
{"choose", (PyCFunction)array_choose,
1836
METH_VARARGS | METH_KEYWORDS, NULL},
1837
{"clip", (PyCFunction)array_clip,
1838
METH_VARARGS | METH_KEYWORDS, NULL},
1839
{"compress", (PyCFunction)array_compress,
1840
METH_VARARGS | METH_KEYWORDS, NULL},
1841
{"conj", (PyCFunction)array_conjugate,
1842
METH_VARARGS, NULL},
1843
{"conjugate", (PyCFunction)array_conjugate,
1844
METH_VARARGS, NULL},
1845
{"copy", (PyCFunction)array_copy,
1846
METH_VARARGS, NULL},
1847
{"cumprod", (PyCFunction)array_cumprod,
1848
METH_VARARGS | METH_KEYWORDS, NULL},
1849
{"cumsum", (PyCFunction)array_cumsum,
1850
METH_VARARGS | METH_KEYWORDS, NULL},
1851
{"diagonal", (PyCFunction)array_diagonal,
1852
METH_VARARGS | METH_KEYWORDS, NULL},
1853
{"fill", (PyCFunction)array_fill,
1854
METH_VARARGS, NULL},
1855
{"flatten", (PyCFunction)array_flatten,
1856
METH_VARARGS, NULL},
1857
{"getfield", (PyCFunction)array_getfield,
1858
METH_VARARGS | METH_KEYWORDS, NULL},
1859
{"item", (PyCFunction)array_toscalar,
1860
METH_VARARGS, NULL},
1861
{"itemset", (PyCFunction) array_setscalar,
1862
METH_VARARGS, NULL},
1863
{"max", (PyCFunction)array_max,
1864
METH_VARARGS | METH_KEYWORDS, NULL},
1865
{"mean", (PyCFunction)array_mean,
1866
METH_VARARGS | METH_KEYWORDS, NULL},
1867
{"min", (PyCFunction)array_min,
1868
METH_VARARGS | METH_KEYWORDS, NULL},
1869
{"newbyteorder", (PyCFunction)array_newbyteorder,
1870
METH_VARARGS, NULL},
1871
{"nonzero", (PyCFunction)array_nonzero,
1872
METH_VARARGS, NULL},
1873
{"prod", (PyCFunction)array_prod,
1874
METH_VARARGS | METH_KEYWORDS, NULL},
1875
{"ptp", (PyCFunction)array_ptp,
1876
METH_VARARGS | METH_KEYWORDS, NULL},
1877
{"put", (PyCFunction)array_put,
1878
METH_VARARGS | METH_KEYWORDS, NULL},
1879
{"ravel", (PyCFunction)array_ravel,
1880
METH_VARARGS, NULL},
1881
{"repeat", (PyCFunction)array_repeat,
1882
METH_VARARGS | METH_KEYWORDS, NULL},
1883
{"reshape", (PyCFunction)array_reshape,
1884
METH_VARARGS | METH_KEYWORDS, NULL},
1885
{"resize", (PyCFunction)array_resize,
1886
METH_VARARGS | METH_KEYWORDS, NULL},
1887
{"round", (PyCFunction)array_round,
1888
METH_VARARGS | METH_KEYWORDS, NULL},
1889
{"searchsorted", (PyCFunction)array_searchsorted,
1890
METH_VARARGS | METH_KEYWORDS, NULL},
1891
{"setfield", (PyCFunction)array_setfield,
1892
METH_VARARGS | METH_KEYWORDS, NULL},
1893
{"setflags", (PyCFunction)array_setflags,
1894
METH_VARARGS | METH_KEYWORDS, NULL},
1895
{"sort", (PyCFunction)array_sort,
1896
METH_VARARGS | METH_KEYWORDS, NULL},
1897
{"squeeze", (PyCFunction)array_squeeze,
1898
METH_VARARGS, NULL},
1899
{"std", (PyCFunction)array_stddev,
1900
METH_VARARGS | METH_KEYWORDS, NULL},
1901
{"sum", (PyCFunction)array_sum,
1902
METH_VARARGS | METH_KEYWORDS, NULL},
1903
{"swapaxes", (PyCFunction)array_swapaxes,
1904
METH_VARARGS, NULL},
1905
{"take", (PyCFunction)array_take,
1906
METH_VARARGS | METH_KEYWORDS, NULL},
1907
{"tofile", (PyCFunction)array_tofile,
1908
METH_VARARGS | METH_KEYWORDS, NULL},
1909
{"tolist", (PyCFunction)array_tolist,
1910
METH_VARARGS, NULL},
1911
{"tostring", (PyCFunction)array_tostring,
1912
METH_VARARGS | METH_KEYWORDS, NULL},
1913
{"trace", (PyCFunction)array_trace,
1914
METH_VARARGS | METH_KEYWORDS, NULL},
1915
{"transpose", (PyCFunction)array_transpose,
1916
METH_VARARGS, NULL},
1917
{"var", (PyCFunction)array_variance,
1918
METH_VARARGS | METH_KEYWORDS, NULL},
1919
{"view", (PyCFunction)array_view,
1920
METH_VARARGS, NULL},
1921
{NULL, NULL} /* sentinel */
1901
{"__array__", (PyCFunction)array_getarray,
1902
METH_VARARGS, NULL},
1903
{"__array_wrap__", (PyCFunction)array_wraparray,
1904
METH_VARARGS, NULL},
1906
/* for the copy module */
1907
{"__copy__", (PyCFunction)array_copy,
1908
METH_VARARGS, NULL},
1909
{"__deepcopy__", (PyCFunction)array_deepcopy,
1910
METH_VARARGS, NULL},
1913
{"__reduce__", (PyCFunction) array_reduce,
1914
METH_VARARGS, NULL},
1915
{"__setstate__", (PyCFunction) array_setstate,
1916
METH_VARARGS, NULL},
1917
{"dumps", (PyCFunction) array_dumps,
1918
METH_VARARGS, NULL},
1919
{"dump", (PyCFunction) array_dump,
1920
METH_VARARGS, NULL},
1922
/* Original and Extended methods added 2005 */
1923
{"all", (PyCFunction)array_all,
1924
METH_VARARGS | METH_KEYWORDS, NULL},
1925
{"any", (PyCFunction)array_any,
1926
METH_VARARGS | METH_KEYWORDS, NULL},
1927
{"argmax", (PyCFunction)array_argmax,
1928
METH_VARARGS | METH_KEYWORDS, NULL},
1929
{"argmin", (PyCFunction)array_argmin,
1930
METH_VARARGS | METH_KEYWORDS, NULL},
1931
{"argsort", (PyCFunction)array_argsort,
1932
METH_VARARGS | METH_KEYWORDS, NULL},
1933
{"astype", (PyCFunction)array_cast,
1934
METH_VARARGS, NULL},
1935
{"byteswap", (PyCFunction)array_byteswap,
1936
METH_VARARGS, NULL},
1937
{"choose", (PyCFunction)array_choose,
1938
METH_VARARGS | METH_KEYWORDS, NULL},
1939
{"clip", (PyCFunction)array_clip,
1940
METH_VARARGS | METH_KEYWORDS, NULL},
1941
{"compress", (PyCFunction)array_compress,
1942
METH_VARARGS | METH_KEYWORDS, NULL},
1943
{"conj", (PyCFunction)array_conjugate,
1944
METH_VARARGS, NULL},
1945
{"conjugate", (PyCFunction)array_conjugate,
1946
METH_VARARGS, NULL},
1947
{"copy", (PyCFunction)array_copy,
1948
METH_VARARGS, NULL},
1949
{"cumprod", (PyCFunction)array_cumprod,
1950
METH_VARARGS | METH_KEYWORDS, NULL},
1951
{"cumsum", (PyCFunction)array_cumsum,
1952
METH_VARARGS | METH_KEYWORDS, NULL},
1953
{"diagonal", (PyCFunction)array_diagonal,
1954
METH_VARARGS | METH_KEYWORDS, NULL},
1955
{"fill", (PyCFunction)array_fill,
1956
METH_VARARGS, NULL},
1957
{"flatten", (PyCFunction)array_flatten,
1958
METH_VARARGS, NULL},
1959
{"getfield", (PyCFunction)array_getfield,
1960
METH_VARARGS | METH_KEYWORDS, NULL},
1961
{"item", (PyCFunction)array_toscalar,
1962
METH_VARARGS, NULL},
1963
{"itemset", (PyCFunction) array_setscalar,
1964
METH_VARARGS, NULL},
1965
{"max", (PyCFunction)array_max,
1966
METH_VARARGS | METH_KEYWORDS, NULL},
1967
{"mean", (PyCFunction)array_mean,
1968
METH_VARARGS | METH_KEYWORDS, NULL},
1969
{"min", (PyCFunction)array_min,
1970
METH_VARARGS | METH_KEYWORDS, NULL},
1971
{"newbyteorder", (PyCFunction)array_newbyteorder,
1972
METH_VARARGS, NULL},
1973
{"nonzero", (PyCFunction)array_nonzero,
1974
METH_VARARGS, NULL},
1975
{"prod", (PyCFunction)array_prod,
1976
METH_VARARGS | METH_KEYWORDS, NULL},
1977
{"ptp", (PyCFunction)array_ptp,
1978
METH_VARARGS | METH_KEYWORDS, NULL},
1979
{"put", (PyCFunction)array_put,
1980
METH_VARARGS | METH_KEYWORDS, NULL},
1981
{"ravel", (PyCFunction)array_ravel,
1982
METH_VARARGS, NULL},
1983
{"repeat", (PyCFunction)array_repeat,
1984
METH_VARARGS | METH_KEYWORDS, NULL},
1985
{"reshape", (PyCFunction)array_reshape,
1986
METH_VARARGS | METH_KEYWORDS, NULL},
1987
{"resize", (PyCFunction)array_resize,
1988
METH_VARARGS | METH_KEYWORDS, NULL},
1989
{"round", (PyCFunction)array_round,
1990
METH_VARARGS | METH_KEYWORDS, NULL},
1991
{"searchsorted", (PyCFunction)array_searchsorted,
1992
METH_VARARGS | METH_KEYWORDS, NULL},
1993
{"setfield", (PyCFunction)array_setfield,
1994
METH_VARARGS | METH_KEYWORDS, NULL},
1995
{"setflags", (PyCFunction)array_setflags,
1996
METH_VARARGS | METH_KEYWORDS, NULL},
1997
{"sort", (PyCFunction)array_sort,
1998
METH_VARARGS | METH_KEYWORDS, NULL},
1999
{"squeeze", (PyCFunction)array_squeeze,
2000
METH_VARARGS, NULL},
2001
{"std", (PyCFunction)array_stddev,
2002
METH_VARARGS | METH_KEYWORDS, NULL},
2003
{"sum", (PyCFunction)array_sum,
2004
METH_VARARGS | METH_KEYWORDS, NULL},
2005
{"swapaxes", (PyCFunction)array_swapaxes,
2006
METH_VARARGS, NULL},
2007
{"take", (PyCFunction)array_take,
2008
METH_VARARGS | METH_KEYWORDS, NULL},
2009
{"tofile", (PyCFunction)array_tofile,
2010
METH_VARARGS | METH_KEYWORDS, NULL},
2011
{"tolist", (PyCFunction)array_tolist,
2012
METH_VARARGS, NULL},
2013
{"tostring", (PyCFunction)array_tostring,
2014
METH_VARARGS | METH_KEYWORDS, NULL},
2015
{"trace", (PyCFunction)array_trace,
2016
METH_VARARGS | METH_KEYWORDS, NULL},
2017
{"transpose", (PyCFunction)array_transpose,
2018
METH_VARARGS, NULL},
2019
{"var", (PyCFunction)array_variance,
2020
METH_VARARGS | METH_KEYWORDS, NULL},
2021
{"view", (PyCFunction)array_view,
2022
METH_VARARGS | METH_KEYWORDS, NULL},
2023
{NULL, NULL} /* sentinel */