summaryrefslogtreecommitdiff
path: root/numpy
diff options
context:
space:
mode:
Diffstat (limited to 'numpy')
-rw-r--r--numpy/core/arrayprint.py11
-rw-r--r--numpy/core/include/numpy/ndarrayobject.h2
-rw-r--r--numpy/core/src/multiarray/ctors.c30
-rw-r--r--numpy/core/src/multiarray/datetime.c239
-rw-r--r--numpy/core/src/umath/scalarmath.c.src60
-rw-r--r--numpy/core/tests/test_multiarray.py13
-rw-r--r--numpy/distutils/command/build_src.py8
-rw-r--r--numpy/random/generator.pyx6
-rw-r--r--numpy/random/tests/test_generator_mt19937.py9
9 files changed, 171 insertions, 207 deletions
diff --git a/numpy/core/arrayprint.py b/numpy/core/arrayprint.py
index b1310a737..233d139fd 100644
--- a/numpy/core/arrayprint.py
+++ b/numpy/core/arrayprint.py
@@ -200,6 +200,8 @@ def set_printoptions(precision=None, threshold=None, edgeitems=None,
-----
`formatter` is always reset with a call to `set_printoptions`.
+ Use `printoptions` as a context manager to set the values temporarily.
+
Examples
--------
Floating point precision can be set:
@@ -236,9 +238,16 @@ def set_printoptions(precision=None, threshold=None, edgeitems=None,
To put back the default options, you can use:
- >>> np.set_printoptions(edgeitems=3,infstr='inf',
+ >>> np.set_printoptions(edgeitems=3, infstr='inf',
... linewidth=75, nanstr='nan', precision=8,
... suppress=False, threshold=1000, formatter=None)
+
+ Also to temporarily override options, use `printoptions` as a context manager:
+
+ >>> with np.printoptions(precision=2, suppress=True, threshold=5):
+ ... np.linspace(0, 10, 10)
+ array([ 0. , 1.11, 2.22, ..., 7.78, 8.89, 10. ])
+
"""
legacy = kwarg.pop('legacy', None)
if kwarg:
diff --git a/numpy/core/include/numpy/ndarrayobject.h b/numpy/core/include/numpy/ndarrayobject.h
index 2cc7ced35..95e9cb060 100644
--- a/numpy/core/include/numpy/ndarrayobject.h
+++ b/numpy/core/include/numpy/ndarrayobject.h
@@ -23,7 +23,7 @@ extern "C" {
/* C-API that requires previous API to be defined */
-#define PyArray_DescrCheck(op) (((PyObject*)(op))->ob_type==&PyArrayDescr_Type)
+#define PyArray_DescrCheck(op) PyObject_TypeCheck(op, &PyArrayDescr_Type)
#define PyArray_Check(op) PyObject_TypeCheck(op, &PyArray_Type)
#define PyArray_CheckExact(op) (((PyObject*)(op))->ob_type == &PyArray_Type)
diff --git a/numpy/core/src/multiarray/ctors.c b/numpy/core/src/multiarray/ctors.c
index ba5121306..5174bd889 100644
--- a/numpy/core/src/multiarray/ctors.c
+++ b/numpy/core/src/multiarray/ctors.c
@@ -3580,6 +3580,7 @@ array_fromfile_binary(FILE *fp, PyArray_Descr *dtype, npy_intp num, size_t *nrea
{
PyArrayObject *r;
npy_off_t start, numbytes;
+ int elsize;
if (num < 0) {
int fail = 0;
@@ -3606,16 +3607,21 @@ array_fromfile_binary(FILE *fp, PyArray_Descr *dtype, npy_intp num, size_t *nrea
}
num = numbytes / dtype->elsize;
}
+
+ /*
+ * Array creation may move sub-array dimensions from the dtype to array
+ * dimensions, so we need to use the original element size when reading.
+ */
+ elsize = dtype->elsize;
+
r = (PyArrayObject *)PyArray_NewFromDescr(&PyArray_Type, dtype, 1, &num,
NULL, NULL, 0, NULL);
if (r == NULL) {
return NULL;
}
- /* In some cases NewFromDescr can replace the dtype, so fetch new one */
- dtype = PyArray_DESCR(r);
NPY_BEGIN_ALLOW_THREADS;
- *nread = fread(PyArray_DATA(r), dtype->elsize, num, fp);
+ *nread = fread(PyArray_DATA(r), elsize, num, fp);
NPY_END_ALLOW_THREADS;
return r;
}
@@ -3642,14 +3648,19 @@ array_from_text(PyArray_Descr *dtype, npy_intp num, char *sep, size_t *nread,
size = (num >= 0) ? num : FROM_BUFFER_SIZE;
+ /*
+ * Array creation may move sub-array dimensions from the dtype to array
+ * dimensions, so we need to use the original dtype when reading.
+ */
+ Py_INCREF(dtype);
+
r = (PyArrayObject *)
PyArray_NewFromDescr(&PyArray_Type, dtype, 1, &size,
NULL, NULL, 0, NULL);
if (r == NULL) {
+ Py_DECREF(dtype);
return NULL;
}
- /* In some cases NewFromDescr can replace the dtype, so fetch new one */
- dtype = PyArray_DESCR(r);
clean_sep = swab_separator(sep);
if (clean_sep == NULL) {
@@ -3710,6 +3721,7 @@ array_from_text(PyArray_Descr *dtype, npy_intp num, char *sep, size_t *nread,
if (PyErr_Occurred()) {
/* If an error is already set (unlikely), do not create new one */
Py_DECREF(r);
+ Py_DECREF(dtype);
return NULL;
}
/* 2019-09-12, NumPy 1.18 */
@@ -3721,6 +3733,7 @@ array_from_text(PyArray_Descr *dtype, npy_intp num, char *sep, size_t *nread,
}
fail:
+ Py_DECREF(dtype);
if (err == 1) {
PyErr_NoMemory();
}
@@ -3986,6 +3999,11 @@ PyArray_FromString(char *data, npy_intp slen, PyArray_Descr *dtype,
return NULL;
}
}
+ /*
+ * NewFromDescr may replace dtype to absorb subarray shape
+ * into the array, so get size beforehand.
+ */
+ npy_intp size_to_copy = num*dtype->elsize;
ret = (PyArrayObject *)
PyArray_NewFromDescr(&PyArray_Type, dtype,
1, &num, NULL, NULL,
@@ -3993,7 +4011,7 @@ PyArray_FromString(char *data, npy_intp slen, PyArray_Descr *dtype,
if (ret == NULL) {
return NULL;
}
- memcpy(PyArray_DATA(ret), data, num*dtype->elsize);
+ memcpy(PyArray_DATA(ret), data, size_to_copy);
}
else {
/* read from character-based string */
diff --git a/numpy/core/src/multiarray/datetime.c b/numpy/core/src/multiarray/datetime.c
index 82e046ca1..d21bb9776 100644
--- a/numpy/core/src/multiarray/datetime.c
+++ b/numpy/core/src/multiarray/datetime.c
@@ -27,6 +27,40 @@
#include "datetime_strings.h"
/*
+ * Computes the python `ret, d = divmod(d, unit)`.
+ *
+ * Note that GCC is smart enough at -O2 to eliminate the `if(*d < 0)` branch
+ * for subsequent calls to this command - it is able to deduce that `*d >= 0`.
+ */
+static inline
+npy_int64 extract_unit_64(npy_int64 *d, npy_int64 unit) {
+ assert(unit > 0);
+ npy_int64 div = *d / unit;
+ npy_int64 mod = *d % unit;
+ if (mod < 0) {
+ mod += unit;
+ div -= 1;
+ }
+ assert(mod >= 0);
+ *d = mod;
+ return div;
+}
+
+static inline
+npy_int32 extract_unit_32(npy_int32 *d, npy_int32 unit) {
+ assert(unit > 0);
+ npy_int32 div = *d / unit;
+ npy_int32 mod = *d % unit;
+ if (mod < 0) {
+ mod += unit;
+ div -= 1;
+ }
+ assert(mod >= 0);
+ *d = mod;
+ return div;
+}
+
+/*
* Imports the PyDateTime functions so we can create these objects.
* This is called during module initialization
*/
@@ -160,17 +194,7 @@ days_to_yearsdays(npy_int64 *days_)
npy_int64 year;
/* Break down the 400 year cycle to get the year and day within the year */
- if (days >= 0) {
- year = 400 * (days / days_per_400years);
- days = days % days_per_400years;
- }
- else {
- year = 400 * ((days - (days_per_400years - 1)) / days_per_400years);
- days = days % days_per_400years;
- if (days < 0) {
- days += days_per_400years;
- }
- }
+ year = 400 * extract_unit_64(&days, days_per_400years);
/* Work out the year/day within the 400 year cycle */
if (days >= 366) {
@@ -411,26 +435,6 @@ PyArray_TimedeltaStructToTimedelta(
}
/*
- * Computes the python `ret, d = divmod(d, unit)`.
- *
- * Note that GCC is smart enough at -O2 to eliminate the `if(*d < 0)` branch
- * for subsequent calls to this command - it is able to deduce that `*d >= 0`.
- */
-static inline
-npy_int64 extract_unit(npy_datetime *d, npy_datetime unit) {
- assert(unit > 0);
- npy_int64 div = *d / unit;
- npy_int64 mod = *d % unit;
- if (mod < 0) {
- mod += unit;
- div -= 1;
- }
- assert(mod >= 0);
- *d = mod;
- return div;
-}
-
-/*
* Converts a datetime based on the given metadata into a datetimestruct
*/
NPY_NO_EXPORT int
@@ -438,7 +442,7 @@ convert_datetime_to_datetimestruct(PyArray_DatetimeMetaData *meta,
npy_datetime dt,
npy_datetimestruct *out)
{
- npy_int64 perday;
+ npy_int64 days;
/* Initialize the output to all zeros */
memset(out, 0, sizeof(npy_datetimestruct));
@@ -473,7 +477,7 @@ convert_datetime_to_datetimestruct(PyArray_DatetimeMetaData *meta,
break;
case NPY_FR_M:
- out->year = 1970 + extract_unit(&dt, 12);
+ out->year = 1970 + extract_unit_64(&dt, 12);
out->month = dt + 1;
break;
@@ -487,73 +491,67 @@ convert_datetime_to_datetimestruct(PyArray_DatetimeMetaData *meta,
break;
case NPY_FR_h:
- perday = 24LL;
-
- set_datetimestruct_days(extract_unit(&dt, perday), out);
+ days = extract_unit_64(&dt, 24LL);
+ set_datetimestruct_days(days, out);
out->hour = (int)dt;
break;
case NPY_FR_m:
- perday = 24LL * 60;
-
- set_datetimestruct_days(extract_unit(&dt, perday), out);
- out->hour = (int)extract_unit(&dt, 60);
- out->min = (int)dt;
+ days = extract_unit_64(&dt, 60LL*24);
+ set_datetimestruct_days(days, out);
+ out->hour = (int)extract_unit_64(&dt, 60LL);
+ out->min = (int)dt;
break;
case NPY_FR_s:
- perday = 24LL * 60 * 60;
-
- set_datetimestruct_days(extract_unit(&dt, perday), out);
- out->hour = (int)extract_unit(&dt, 60*60);
- out->min = (int)extract_unit(&dt, 60);
+ days = extract_unit_64(&dt, 60LL*60*24);
+ set_datetimestruct_days(days, out);
+ out->hour = (int)extract_unit_64(&dt, 60LL*60);
+ out->min = (int)extract_unit_64(&dt, 60LL);
out->sec = (int)dt;
break;
case NPY_FR_ms:
- perday = 24LL * 60 * 60 * 1000;
-
- set_datetimestruct_days(extract_unit(&dt, perday), out);
- out->hour = (int)extract_unit(&dt, 1000LL*60*60);
- out->min = (int)extract_unit(&dt, 1000LL*60);
- out->sec = (int)extract_unit(&dt, 1000LL);
+ days = extract_unit_64(&dt, 1000LL*60*60*24);
+ set_datetimestruct_days(days, out);
+ out->hour = (int)extract_unit_64(&dt, 1000LL*60*60);
+ out->min = (int)extract_unit_64(&dt, 1000LL*60);
+ out->sec = (int)extract_unit_64(&dt, 1000LL);
out->us = (int)(dt * 1000);
break;
case NPY_FR_us:
- perday = 24LL * 60LL * 60LL * 1000LL * 1000LL;
- set_datetimestruct_days(extract_unit(&dt, perday), out);
- out->hour = (int)extract_unit(&dt, 1000LL*1000*60*60);
- out->min = (int)extract_unit(&dt, 1000LL*1000*60);
- out->sec = (int)extract_unit(&dt, 1000LL*1000);
+ days = extract_unit_64(&dt, 1000LL*1000*60*60*24);
+ set_datetimestruct_days(days, out);
+ out->hour = (int)extract_unit_64(&dt, 1000LL*1000*60*60);
+ out->min = (int)extract_unit_64(&dt, 1000LL*1000*60);
+ out->sec = (int)extract_unit_64(&dt, 1000LL*1000);
out->us = (int)dt;
break;
case NPY_FR_ns:
- perday = 24LL * 60LL * 60LL * 1000LL * 1000LL * 1000LL;
-
- set_datetimestruct_days(extract_unit(&dt, perday), out);
- out->hour = (int)extract_unit(&dt, 1000LL*1000*1000*60*60);
- out->min = (int)extract_unit(&dt, 1000LL*1000*1000*60);
- out->sec = (int)extract_unit(&dt, 1000LL*1000*1000);
- out->us = (int)extract_unit(&dt, 1000LL);
+ days = extract_unit_64(&dt, 1000LL*1000*1000*60*60*24);
+ set_datetimestruct_days(days, out);
+ out->hour = (int)extract_unit_64(&dt, 1000LL*1000*1000*60*60);
+ out->min = (int)extract_unit_64(&dt, 1000LL*1000*1000*60);
+ out->sec = (int)extract_unit_64(&dt, 1000LL*1000*1000);
+ out->us = (int)extract_unit_64(&dt, 1000LL);
out->ps = (int)(dt * 1000);
break;
case NPY_FR_ps:
- perday = 24LL * 60 * 60 * 1000 * 1000 * 1000 * 1000;
-
- set_datetimestruct_days(extract_unit(&dt, perday), out);
- out->hour = (int)extract_unit(&dt, 1000LL*1000*1000*1000*60*60);
- out->min = (int)extract_unit(&dt, 1000LL*1000*1000*1000*60);
- out->sec = (int)extract_unit(&dt, 1000LL*1000*1000*1000);
- out->us = (int)extract_unit(&dt, 1000LL*1000);
+ days = extract_unit_64(&dt, 1000LL*1000*1000*1000*60*60*24);
+ set_datetimestruct_days(days, out);
+ out->hour = (int)extract_unit_64(&dt, 1000LL*1000*1000*1000*60*60);
+ out->min = (int)extract_unit_64(&dt, 1000LL*1000*1000*1000*60);
+ out->sec = (int)extract_unit_64(&dt, 1000LL*1000*1000*1000);
+ out->us = (int)extract_unit_64(&dt, 1000LL*1000);
out->ps = (int)(dt);
break;
case NPY_FR_fs:
/* entire range is only +- 2.6 hours */
- out->hour = (int)extract_unit(&dt, 1000LL*1000*1000*1000*1000*60*60);
+ out->hour = (int)extract_unit_64(&dt, 1000LL*1000*1000*1000*1000*60*60);
if (out->hour < 0) {
out->year = 1969;
out->month = 12;
@@ -561,16 +559,16 @@ convert_datetime_to_datetimestruct(PyArray_DatetimeMetaData *meta,
out->hour += 24;
assert(out->hour >= 0);
}
- out->min = (int)extract_unit(&dt, 1000LL*1000*1000*1000*1000*60);
- out->sec = (int)extract_unit(&dt, 1000LL*1000*1000*1000*1000);
- out->us = (int)extract_unit(&dt, 1000LL*1000*1000);
- out->ps = (int)extract_unit(&dt, 1000LL);
+ out->min = (int)extract_unit_64(&dt, 1000LL*1000*1000*1000*1000*60);
+ out->sec = (int)extract_unit_64(&dt, 1000LL*1000*1000*1000*1000);
+ out->us = (int)extract_unit_64(&dt, 1000LL*1000*1000);
+ out->ps = (int)extract_unit_64(&dt, 1000LL);
out->as = (int)(dt * 1000);
break;
case NPY_FR_as:
/* entire range is only +- 9.2 seconds */
- out->sec = (int)extract_unit(&dt, 1000LL*1000*1000*1000*1000*1000);
+ out->sec = (int)extract_unit_64(&dt, 1000LL*1000*1000*1000*1000*1000);
if (out->sec < 0) {
out->year = 1969;
out->month = 12;
@@ -580,8 +578,8 @@ convert_datetime_to_datetimestruct(PyArray_DatetimeMetaData *meta,
out->sec += 60;
assert(out->sec >= 0);
}
- out->us = (int)extract_unit(&dt, 1000LL*1000*1000*1000);
- out->ps = (int)extract_unit(&dt, 1000LL*1000);
+ out->us = (int)extract_unit_64(&dt, 1000LL*1000*1000*1000);
+ out->ps = (int)extract_unit_64(&dt, 1000LL*1000);
out->as = (int)dt;
break;
@@ -2017,20 +2015,8 @@ add_seconds_to_datetimestruct(npy_datetimestruct *dts, int seconds)
int minutes;
dts->sec += seconds;
- if (dts->sec < 0) {
- minutes = dts->sec / 60;
- dts->sec = dts->sec % 60;
- if (dts->sec < 0) {
- --minutes;
- dts->sec += 60;
- }
- add_minutes_to_datetimestruct(dts, minutes);
- }
- else if (dts->sec >= 60) {
- minutes = dts->sec / 60;
- dts->sec = dts->sec % 60;
- add_minutes_to_datetimestruct(dts, minutes);
- }
+ minutes = extract_unit_32(&dts->sec, 60);
+ add_minutes_to_datetimestruct(dts, minutes);
}
/*
@@ -2042,28 +2028,13 @@ add_minutes_to_datetimestruct(npy_datetimestruct *dts, int minutes)
{
int isleap;
- /* MINUTES */
dts->min += minutes;
- while (dts->min < 0) {
- dts->min += 60;
- dts->hour--;
- }
- while (dts->min >= 60) {
- dts->min -= 60;
- dts->hour++;
- }
- /* HOURS */
- while (dts->hour < 0) {
- dts->hour += 24;
- dts->day--;
- }
- while (dts->hour >= 24) {
- dts->hour -= 24;
- dts->day++;
- }
+ /* propagate invalid minutes into hour and day changes */
+ dts->hour += extract_unit_32(&dts->min, 60);
+ dts->day += extract_unit_32(&dts->hour, 24);
- /* DAYS */
+ /* propagate invalid days into month and year changes */
if (dts->day < 1) {
dts->month--;
if (dts->month < 1) {
@@ -2890,7 +2861,6 @@ convert_datetime_to_pyobject(npy_datetime dt, PyArray_DatetimeMetaData *meta)
NPY_NO_EXPORT PyObject *
convert_timedelta_to_pyobject(npy_timedelta td, PyArray_DatetimeMetaData *meta)
{
- PyObject *ret = NULL;
npy_timedelta value;
int days = 0, seconds = 0, useconds = 0;
@@ -2920,54 +2890,47 @@ convert_timedelta_to_pyobject(npy_timedelta td, PyArray_DatetimeMetaData *meta)
/* Convert to days/seconds/useconds */
switch (meta->base) {
case NPY_FR_W:
- value *= 7;
+ days = value * 7;
break;
case NPY_FR_D:
+ days = value;
break;
case NPY_FR_h:
- seconds = (int)((value % 24) * (60*60));
- value = value / 24;
+ days = extract_unit_64(&value, 24ULL);
+ seconds = value*60*60;
break;
case NPY_FR_m:
- seconds = (int)(value % (24*60)) * 60;
- value = value / (24*60);
+ days = extract_unit_64(&value, 60ULL*24);
+ seconds = value*60;
break;
case NPY_FR_s:
- seconds = (int)(value % (24*60*60));
- value = value / (24*60*60);
+ days = extract_unit_64(&value, 60ULL*60*24);
+ seconds = value;
break;
case NPY_FR_ms:
- useconds = (int)(value % 1000) * 1000;
- value = value / 1000;
- seconds = (int)(value % (24*60*60));
- value = value / (24*60*60);
+ days = extract_unit_64(&value, 1000ULL*60*60*24);
+ seconds = extract_unit_64(&value, 1000ULL);
+ useconds = value*1000;
break;
case NPY_FR_us:
- useconds = (int)(value % (1000*1000));
- value = value / (1000*1000);
- seconds = (int)(value % (24*60*60));
- value = value / (24*60*60);
+ days = extract_unit_64(&value, 1000ULL*1000*60*60*24);
+ seconds = extract_unit_64(&value, 1000ULL*1000);
+ useconds = value;
break;
default:
+ // unreachable, handled by the `if` above
+ assert(NPY_FALSE);
break;
}
/*
- * 'value' represents days, and seconds/useconds are filled.
- *
* If it would overflow the datetime.timedelta days, return a raw int
*/
- if (value < -999999999 || value > 999999999) {
+ if (days < -999999999 || days > 999999999) {
return PyLong_FromLongLong(td);
}
else {
- days = (int)value;
- ret = PyDelta_FromDSU(days, seconds, useconds);
- if (ret == NULL) {
- return NULL;
- }
+ return PyDelta_FromDSU(days, seconds, useconds);
}
-
- return ret;
}
/*
diff --git a/numpy/core/src/umath/scalarmath.c.src b/numpy/core/src/umath/scalarmath.c.src
index 9cce0b7f0..d5d8d659b 100644
--- a/numpy/core/src/umath/scalarmath.c.src
+++ b/numpy/core/src/umath/scalarmath.c.src
@@ -406,21 +406,22 @@ half_ctype_divmod(npy_half a, npy_half b, npy_half *out1, npy_half *out2) {
/**begin repeat
* #name = float, double, longdouble#
* #type = npy_float, npy_double, npy_longdouble#
+ * #c = f,,l#
*/
-static npy_@name@ (*_basic_@name@_pow)(@type@ a, @type@ b);
static void
@name@_ctype_power(@type@ a, @type@ b, @type@ *out)
{
- *out = _basic_@name@_pow(a, b);
+ *out = npy_pow@c@(a, b);
}
+
/**end repeat**/
static void
half_ctype_power(npy_half a, npy_half b, npy_half *out)
{
const npy_float af = npy_half_to_float(a);
const npy_float bf = npy_half_to_float(b);
- const npy_float outf = _basic_float_pow(af,bf);
+ const npy_float outf = npy_powf(af,bf);
*out = npy_float_to_half(outf);
}
@@ -477,14 +478,10 @@ static void
}
/**end repeat**/
-/*
- * Get the nc_powf, nc_pow, and nc_powl functions from
- * the data area of the power ufunc in umathmodule.
- */
-
/**begin repeat
* #name = cfloat, cdouble, clongdouble#
* #type = npy_cfloat, npy_cdouble, npy_clongdouble#
+ * #c = f,,l#
*/
static void
@name@_ctype_positive(@type@ a, @type@ *out)
@@ -493,12 +490,10 @@ static void
out->imag = a.imag;
}
-static void (*_basic_@name@_pow)(@type@ *, @type@ *, @type@ *);
-
static void
@name@_ctype_power(@type@ a, @type@ b, @type@ *out)
{
- _basic_@name@_pow(&a, &b, out);
+ *out = npy_cpow@c@(a, b);
}
/**end repeat**/
@@ -1680,52 +1675,9 @@ add_scalarmath(void)
/**end repeat**/
}
-static int
-get_functions(PyObject * mm)
-{
- PyObject *obj;
- void **funcdata;
- char *signatures;
- int i, j;
- int ret = -1;
-
- /* Get the nc_pow functions */
- /* Get the pow functions */
- obj = PyObject_GetAttrString(mm, "power");
- if (obj == NULL) {
- goto fail;
- }
- funcdata = ((PyUFuncObject *)obj)->data;
- signatures = ((PyUFuncObject *)obj)->types;
-
- i = 0;
- j = 0;
- while (signatures[i] != NPY_FLOAT) {
- i += 3;
- j++;
- }
- _basic_float_pow = funcdata[j];
- _basic_double_pow = funcdata[j + 1];
- _basic_longdouble_pow = funcdata[j + 2];
- _basic_cfloat_pow = funcdata[j + 3];
- _basic_cdouble_pow = funcdata[j + 4];
- _basic_clongdouble_pow = funcdata[j + 5];
- Py_DECREF(obj);
-
- return ret = 0;
-
- fail:
- Py_DECREF(mm);
- return ret;
-}
-
NPY_NO_EXPORT int initscalarmath(PyObject * m)
{
- if (get_functions(m) < 0) {
- return -1;
- }
-
add_scalarmath();
return 0;
diff --git a/numpy/core/tests/test_multiarray.py b/numpy/core/tests/test_multiarray.py
index 88db357b2..9b124f603 100644
--- a/numpy/core/tests/test_multiarray.py
+++ b/numpy/core/tests/test_multiarray.py
@@ -5023,6 +5023,19 @@ class TestIO(object):
self.test_tofile_sep()
self.test_tofile_format()
+ def test_fromfile_subarray_binary(self):
+ # Test subarray dtypes which are absorbed into the shape
+ x = np.arange(24, dtype="i4").reshape(2, 3, 4)
+ x.tofile(self.filename)
+ res = np.fromfile(self.filename, dtype="(3,4)i4")
+ assert_array_equal(x, res)
+
+ x_str = x.tobytes()
+ with assert_warns(DeprecationWarning):
+ # binary fromstring is deprecated
+ res = np.fromstring(x_str, dtype="(3,4)i4")
+ assert_array_equal(x, res)
+
class TestFromBuffer(object):
@pytest.mark.parametrize('byteorder', ['<', '>'])
diff --git a/numpy/distutils/command/build_src.py b/numpy/distutils/command/build_src.py
index af8cec08a..3e0522c5f 100644
--- a/numpy/distutils/command/build_src.py
+++ b/numpy/distutils/command/build_src.py
@@ -53,12 +53,12 @@ class build_src(build_ext.build_ext):
('inplace', 'i',
"ignore build-lib and put compiled extensions into the source " +
"directory alongside your pure Python modules"),
- ('verbose', 'v',
+ ('verbose-cfg', None,
"change logging level from WARN to INFO which will show all " +
"compiler output")
]
- boolean_options = ['force', 'inplace', 'verbose']
+ boolean_options = ['force', 'inplace', 'verbose-cfg']
help_options = []
@@ -79,7 +79,7 @@ class build_src(build_ext.build_ext):
self.swig_opts = None
self.swig_cpp = None
self.swig = None
- self.verbose = None
+ self.verbose_cfg = None
def finalize_options(self):
self.set_undefined_options('build',
@@ -370,7 +370,7 @@ class build_src(build_ext.build_ext):
+name.split('.')[:-1]))
self.mkpath(build_dir)
- if self.verbose:
+ if self.verbose_cfg:
new_level = log.INFO
else:
new_level = log.WARN
diff --git a/numpy/random/generator.pyx b/numpy/random/generator.pyx
index 37ac57c06..df7485a97 100644
--- a/numpy/random/generator.pyx
+++ b/numpy/random/generator.pyx
@@ -3786,7 +3786,7 @@ cdef class Generator:
# Shuffling and permutations:
def shuffle(self, object x, axis=0):
"""
- shuffle(x)
+ shuffle(x, axis=0)
Modify a sequence in-place by shuffling its contents.
@@ -3858,7 +3858,7 @@ cdef class Generator:
x = np.swapaxes(x, 0, axis)
buf = np.empty_like(x[0, ...])
with self.lock:
- for i in reversed(range(1, n)):
+ for i in reversed(range(1, len(x))):
j = random_interval(&self._bitgen, i)
if i == j:
# i == j is not needed and memcpy is undefined.
@@ -3928,7 +3928,7 @@ cdef class Generator:
def permutation(self, object x, axis=0):
"""
- permutation(x)
+ permutation(x, axis=0)
Randomly permute a sequence, or return a permuted range.
diff --git a/numpy/random/tests/test_generator_mt19937.py b/numpy/random/tests/test_generator_mt19937.py
index 20bc10cd0..391c33c1a 100644
--- a/numpy/random/tests/test_generator_mt19937.py
+++ b/numpy/random/tests/test_generator_mt19937.py
@@ -746,6 +746,15 @@ class TestRandomDist(object):
random.shuffle(actual, axis=-1)
assert_array_equal(actual, desired)
+ def test_shuffle_axis_nonsquare(self):
+ y1 = np.arange(20).reshape(2, 10)
+ y2 = y1.copy()
+ random = Generator(MT19937(self.seed))
+ random.shuffle(y1, axis=1)
+ random = Generator(MT19937(self.seed))
+ random.shuffle(y2.T)
+ assert_array_equal(y1, y2)
+
def test_shuffle_masked(self):
# gh-3263
a = np.ma.masked_values(np.reshape(range(20), (5, 4)) % 3 - 1, -1)