summaryrefslogtreecommitdiff
path: root/numpy
diff options
context:
space:
mode:
Diffstat (limited to 'numpy')
-rw-r--r--numpy/core/numeric.py10
-rw-r--r--numpy/core/records.py5
-rw-r--r--numpy/core/tests/test_errstate.py8
-rw-r--r--numpy/lib/_datasource.py9
-rw-r--r--numpy/lib/function_base.py2
-rw-r--r--numpy/lib/nanfunctions.py27
-rw-r--r--numpy/lib/tests/test_nanfunctions.py28
7 files changed, 81 insertions, 8 deletions
diff --git a/numpy/core/numeric.py b/numpy/core/numeric.py
index 8a8efddf3..1b8f36c3e 100644
--- a/numpy/core/numeric.py
+++ b/numpy/core/numeric.py
@@ -12,6 +12,7 @@ import operator
import sys
import warnings
import numbers
+import contextlib
import numpy as np
from . import multiarray
@@ -2990,7 +2991,7 @@ _Unspecified = _unspecified()
@set_module('numpy')
-class errstate(object):
+class errstate(contextlib.ContextDecorator):
"""
errstate(**kwargs)
@@ -3000,7 +3001,12 @@ class errstate(object):
that context to execute with a known error handling behavior. Upon entering
the context the error handling is set with `seterr` and `seterrcall`, and
upon exiting it is reset to what it was before.
-
+
+ .. versionchanged:: 1.17.0
+ `errstate` is also usable as a function decorator, saving
+ a level of indentation if an entire function is wrapped.
+ See :py:class:`contextlib.ContextDecorator` for more information.
+
Parameters
----------
kwargs : {divide, over, under, invalid}
diff --git a/numpy/core/records.py b/numpy/core/records.py
index 4ea83accc..42aca5b60 100644
--- a/numpy/core/records.py
+++ b/numpy/core/records.py
@@ -721,7 +721,7 @@ def fromstring(datastring, dtype=None, shape=None, offset=0, formats=None,
a string"""
if dtype is None and formats is None:
- raise ValueError("Must have dtype= or formats=")
+ raise TypeError("fromstring() needs a 'dtype' or 'formats' argument")
if dtype is not None:
descr = sb.dtype(dtype)
@@ -768,6 +768,9 @@ def fromfile(fd, dtype=None, shape=None, offset=0, formats=None,
>>> r.shape
(10,)
"""
+
+ if dtype is None and formats is None:
+ raise TypeError("fromfile() needs a 'dtype' or 'formats' argument")
if (shape is None or shape == 0):
shape = (-1,)
diff --git a/numpy/core/tests/test_errstate.py b/numpy/core/tests/test_errstate.py
index 670d485c1..0008c4cc8 100644
--- a/numpy/core/tests/test_errstate.py
+++ b/numpy/core/tests/test_errstate.py
@@ -39,3 +39,11 @@ class TestErrstate(object):
with np.errstate(call=None):
assert_(np.geterrcall() is None, 'call is not None')
assert_(np.geterrcall() is olderrcall, 'call is not olderrcall')
+
+ def test_errstate_decorator(self):
+ @np.errstate(all='ignore')
+ def foo():
+ a = -np.arange(3)
+ a // 0
+
+ foo()
diff --git a/numpy/lib/_datasource.py b/numpy/lib/_datasource.py
index 3a0e67f60..816f7624e 100644
--- a/numpy/lib/_datasource.py
+++ b/numpy/lib/_datasource.py
@@ -547,6 +547,11 @@ class DataSource(object):
is accessible if it exists in either location.
"""
+
+ # First test for local path
+ if os.path.exists(path):
+ return True
+
# We import this here because importing urllib2 is slow and
# a significant fraction of numpy's total import time.
if sys.version_info[0] >= 3:
@@ -556,10 +561,6 @@ class DataSource(object):
from urllib2 import urlopen
from urllib2 import URLError
- # Test local path
- if os.path.exists(path):
- return True
-
# Test cached url
upath = self.abspath(path)
if os.path.exists(upath):
diff --git a/numpy/lib/function_base.py b/numpy/lib/function_base.py
index fa1f42252..b61a64b8e 100644
--- a/numpy/lib/function_base.py
+++ b/numpy/lib/function_base.py
@@ -1150,7 +1150,7 @@ def diff(a, n=1, axis=-1, prepend=np._NoValue, append=np._NoValue):
"""
Calculate the n-th discrete difference along the given axis.
- The first difference is given by ``out[n] = a[n+1] - a[n]`` along
+ The first difference is given by ``out[i] = a[i+1] - a[i]`` along
the given axis, higher differences are calculated by using `diff`
recursively.
diff --git a/numpy/lib/nanfunctions.py b/numpy/lib/nanfunctions.py
index b3bf1880b..77c851fcf 100644
--- a/numpy/lib/nanfunctions.py
+++ b/numpy/lib/nanfunctions.py
@@ -40,6 +40,33 @@ __all__ = [
]
+def _nan_mask(a, out=None):
+ """
+ Parameters
+ ----------
+ a : array-like
+ Input array with at least 1 dimension.
+ out : ndarray, optional
+ Alternate output array in which to place the result. The default
+ is ``None``; if provided, it must have the same shape as the
+ expected output and will prevent the allocation of a new array.
+
+ Returns
+ -------
+ y : bool ndarray or True
+ A bool array where ``np.nan`` positions are marked with ``False``
+ and other positions are marked with ``True``. If the type of ``a``
+ is such that it can't possibly contain ``np.nan``, returns ``True``.
+ """
+ # we assume that a is an array for this private function
+
+ if a.dtype.kind not in 'fc':
+ return True
+
+ y = np.isnan(a, out=out)
+ y = np.invert(y, out=y)
+ return y
+
def _replace_nan(a, val):
"""
If `a` is of inexact type, make a copy of `a`, replace NaNs with
diff --git a/numpy/lib/tests/test_nanfunctions.py b/numpy/lib/tests/test_nanfunctions.py
index 504372faf..b7261c63f 100644
--- a/numpy/lib/tests/test_nanfunctions.py
+++ b/numpy/lib/tests/test_nanfunctions.py
@@ -1,8 +1,10 @@
from __future__ import division, absolute_import, print_function
import warnings
+import pytest
import numpy as np
+from numpy.lib.nanfunctions import _nan_mask
from numpy.testing import (
assert_, assert_equal, assert_almost_equal, assert_no_warnings,
assert_raises, assert_array_equal, suppress_warnings
@@ -925,3 +927,29 @@ class TestNanFunctions_Quantile(object):
p = p.tolist()
np.nanquantile(np.arange(100.), p, interpolation="midpoint")
assert_array_equal(p, p0)
+
+@pytest.mark.parametrize("arr, expected", [
+ # array of floats with some nans
+ (np.array([np.nan, 5.0, np.nan, np.inf]),
+ np.array([False, True, False, True])),
+ # int64 array that can't possibly have nans
+ (np.array([1, 5, 7, 9], dtype=np.int64),
+ True),
+ # bool array that can't possibly have nans
+ (np.array([False, True, False, True]),
+ True),
+ # 2-D complex array with nans
+ (np.array([[np.nan, 5.0],
+ [np.nan, np.inf]], dtype=np.complex64),
+ np.array([[False, True],
+ [False, True]])),
+ ])
+def test__nan_mask(arr, expected):
+ for out in [None, np.empty(arr.shape, dtype=np.bool_)]:
+ actual = _nan_mask(arr, out=out)
+ assert_equal(actual, expected)
+ # the above won't distinguish between True proper
+ # and an array of True values; we want True proper
+ # for types that can't possibly contain NaN
+ if type(expected) is not np.ndarray:
+ assert actual is True