summaryrefslogtreecommitdiff
path: root/numpy/lib/tests/test_nanfunctions.py
diff options
context:
space:
mode:
authorStephan Hoyer <shoyer@climate.com>2015-01-03 18:37:33 +0200
committerStephan Hoyer <shoyer@climate.com>2015-01-05 11:08:16 -0800
commit1b2d2e977d51414121548d4454afdf02d9def3b3 (patch)
tree4cdf43e2cbe8f2ab6df2f95183dfeb23f8e08de3 /numpy/lib/tests/test_nanfunctions.py
parent3ef77eea0d9c2cd76bc9b89b04a32f1322f842d5 (diff)
downloadnumpy-1b2d2e977d51414121548d4454afdf02d9def3b3.tar.gz
ENH: add np.nanprod
This PR adds an implementation of `nanprod`. The actual function is a two-liner adapted from `nansum`. Most of this PR consists of documentation and tests (for which I took the opportunity to do some consolidation). A method with the same functionality exists in pandas, and I was surprised to discover that it's not in numpy.
Diffstat (limited to 'numpy/lib/tests/test_nanfunctions.py')
-rw-r--r--numpy/lib/tests/test_nanfunctions.py229
1 files changed, 81 insertions, 148 deletions
diff --git a/numpy/lib/tests/test_nanfunctions.py b/numpy/lib/tests/test_nanfunctions.py
index 35ae86c20..f418504c2 100644
--- a/numpy/lib/tests/test_nanfunctions.py
+++ b/numpy/lib/tests/test_nanfunctions.py
@@ -236,6 +236,11 @@ class TestNanFunctions_IntTypes(TestCase):
for mat in self.integer_arrays():
assert_equal(np.nansum(mat), tgt)
+ def test_nanprod(self):
+ tgt = np.prod(self.mat)
+ for mat in self.integer_arrays():
+ assert_equal(np.nanprod(mat), tgt)
+
def test_nanmean(self):
tgt = np.mean(self.mat)
for mat in self.integer_arrays():
@@ -260,119 +265,7 @@ class TestNanFunctions_IntTypes(TestCase):
assert_equal(np.nanstd(mat, ddof=1), tgt)
-class TestNanFunctions_Sum(TestCase):
-
- def test_mutation(self):
- # Check that passed array is not modified.
- ndat = _ndat.copy()
- np.nansum(ndat)
- assert_equal(ndat, _ndat)
-
- def test_keepdims(self):
- mat = np.eye(3)
- for axis in [None, 0, 1]:
- tgt = np.sum(mat, axis=axis, keepdims=True)
- res = np.nansum(mat, axis=axis, keepdims=True)
- assert_(res.ndim == tgt.ndim)
-
- def test_out(self):
- mat = np.eye(3)
- resout = np.zeros(3)
- tgt = np.sum(mat, axis=1)
- res = np.nansum(mat, axis=1, out=resout)
- assert_almost_equal(res, resout)
- assert_almost_equal(res, tgt)
-
- def test_dtype_from_dtype(self):
- mat = np.eye(3)
- codes = 'efdgFDG'
- for c in codes:
- tgt = np.sum(mat, dtype=np.dtype(c), axis=1).dtype.type
- res = np.nansum(mat, dtype=np.dtype(c), axis=1).dtype.type
- assert_(res is tgt)
- # scalar case
- tgt = np.sum(mat, dtype=np.dtype(c), axis=None).dtype.type
- res = np.nansum(mat, dtype=np.dtype(c), axis=None).dtype.type
- assert_(res is tgt)
-
- def test_dtype_from_char(self):
- mat = np.eye(3)
- codes = 'efdgFDG'
- for c in codes:
- tgt = np.sum(mat, dtype=c, axis=1).dtype.type
- res = np.nansum(mat, dtype=c, axis=1).dtype.type
- assert_(res is tgt)
- # scalar case
- tgt = np.sum(mat, dtype=c, axis=None).dtype.type
- res = np.nansum(mat, dtype=c, axis=None).dtype.type
- assert_(res is tgt)
-
- def test_dtype_from_input(self):
- codes = 'efdgFDG'
- for c in codes:
- mat = np.eye(3, dtype=c)
- tgt = np.sum(mat, axis=1).dtype.type
- res = np.nansum(mat, axis=1).dtype.type
- assert_(res is tgt)
- # scalar case
- tgt = np.sum(mat, axis=None).dtype.type
- res = np.nansum(mat, axis=None).dtype.type
- assert_(res is tgt)
-
- def test_result_values(self):
- tgt = [np.sum(d) for d in _rdat]
- res = np.nansum(_ndat, axis=1)
- assert_almost_equal(res, tgt)
-
- def test_allnans(self):
- # Check for FutureWarning
- with warnings.catch_warnings(record=True) as w:
- warnings.simplefilter('always')
- res = np.nansum([np.nan]*3, axis=None)
- assert_(res == 0, 'result is not 0')
- assert_(len(w) == 0, 'warning raised')
- # Check scalar
- res = np.nansum(np.nan)
- assert_(res == 0, 'result is not 0')
- assert_(len(w) == 0, 'warning raised')
- # Check there is no warning for not all-nan
- np.nansum([0]*3, axis=None)
- assert_(len(w) == 0, 'unwanted warning raised')
-
- def test_empty(self):
- mat = np.zeros((0, 3))
- tgt = [0]*3
- res = np.nansum(mat, axis=0)
- assert_equal(res, tgt)
- tgt = []
- res = np.nansum(mat, axis=1)
- assert_equal(res, tgt)
- tgt = 0
- res = np.nansum(mat, axis=None)
- assert_equal(res, tgt)
-
- def test_scalar(self):
- assert_(np.nansum(0.) == 0.)
-
- def test_matrices(self):
- # Check that it works and that type and
- # shape are preserved
- mat = np.matrix(np.eye(3))
- res = np.nansum(mat, axis=0)
- assert_(isinstance(res, np.matrix))
- assert_(res.shape == (1, 3))
- res = np.nansum(mat, axis=1)
- assert_(isinstance(res, np.matrix))
- assert_(res.shape == (3, 1))
- res = np.nansum(mat)
- assert_(np.isscalar(res))
-
-
-class TestNanFunctions_MeanVarStd(TestCase):
-
- nanfuncs = [np.nanmean, np.nanvar, np.nanstd]
- stdfuncs = [np.mean, np.var, np.std]
-
+class SharedNanFunctionsTestsMixin(object):
def test_mutation(self):
# Check that passed array is not modified.
ndat = _ndat.copy()
@@ -380,17 +273,6 @@ class TestNanFunctions_MeanVarStd(TestCase):
f(ndat)
assert_equal(ndat, _ndat)
- def test_dtype_error(self):
- for f in self.nanfuncs:
- for dtype in [np.bool_, np.int_, np.object]:
- assert_raises(TypeError, f, _ndat, axis=1, dtype=np.int)
-
- def test_out_dtype_error(self):
- for f in self.nanfuncs:
- for dtype in [np.bool_, np.int_, np.object]:
- out = np.empty(_ndat.shape[0], dtype=dtype)
- assert_raises(TypeError, f, _ndat, axis=1, out=out)
-
def test_keepdims(self):
mat = np.eye(3)
for nf, rf in zip(self.nanfuncs, self.stdfuncs):
@@ -447,6 +329,81 @@ class TestNanFunctions_MeanVarStd(TestCase):
res = nf(mat, axis=None).dtype.type
assert_(res is tgt)
+ def test_result_values(self):
+ for nf, rf in zip(self.nanfuncs, self.stdfuncs):
+ tgt = [rf(d) for d in _rdat]
+ res = nf(_ndat, axis=1)
+ assert_almost_equal(res, tgt)
+
+ def test_scalar(self):
+ for f in self.nanfuncs:
+ assert_(f(0.) == 0.)
+
+ def test_matrices(self):
+ # Check that it works and that type and
+ # shape are preserved
+ mat = np.matrix(np.eye(3))
+ for f in self.nanfuncs:
+ res = f(mat, axis=0)
+ assert_(isinstance(res, np.matrix))
+ assert_(res.shape == (1, 3))
+ res = f(mat, axis=1)
+ assert_(isinstance(res, np.matrix))
+ assert_(res.shape == (3, 1))
+ res = f(mat)
+ assert_(np.isscalar(res))
+
+
+class TestNanFunctions_SumProd(TestCase, SharedNanFunctionsTestsMixin):
+
+ nanfuncs = [np.nansum, np.nanprod]
+ stdfuncs = [np.sum, np.prod]
+
+ def test_allnans(self):
+ # Check for FutureWarning
+ with warnings.catch_warnings(record=True) as w:
+ warnings.simplefilter('always')
+ res = np.nansum([np.nan]*3, axis=None)
+ assert_(res == 0, 'result is not 0')
+ assert_(len(w) == 0, 'warning raised')
+ # Check scalar
+ res = np.nansum(np.nan)
+ assert_(res == 0, 'result is not 0')
+ assert_(len(w) == 0, 'warning raised')
+ # Check there is no warning for not all-nan
+ np.nansum([0]*3, axis=None)
+ assert_(len(w) == 0, 'unwanted warning raised')
+
+ def test_empty(self):
+ for f, tgt_value in zip([np.nansum, np.nanprod], [0, 1]):
+ mat = np.zeros((0, 3))
+ tgt = [tgt_value]*3
+ res = f(mat, axis=0)
+ assert_equal(res, tgt)
+ tgt = []
+ res = f(mat, axis=1)
+ assert_equal(res, tgt)
+ tgt = tgt_value
+ res = f(mat, axis=None)
+ assert_equal(res, tgt)
+
+
+class TestNanFunctions_MeanVarStd(TestCase, SharedNanFunctionsTestsMixin):
+
+ nanfuncs = [np.nanmean, np.nanvar, np.nanstd]
+ stdfuncs = [np.mean, np.var, np.std]
+
+ def test_dtype_error(self):
+ for f in self.nanfuncs:
+ for dtype in [np.bool_, np.int_, np.object]:
+ assert_raises(TypeError, f, _ndat, axis=1, dtype=np.int)
+
+ def test_out_dtype_error(self):
+ for f in self.nanfuncs:
+ for dtype in [np.bool_, np.int_, np.object]:
+ out = np.empty(_ndat.shape[0], dtype=dtype)
+ assert_raises(TypeError, f, _ndat, axis=1, out=out)
+
def test_ddof(self):
nanfuncs = [np.nanvar, np.nanstd]
stdfuncs = [np.var, np.std]
@@ -473,12 +430,6 @@ class TestNanFunctions_MeanVarStd(TestCase):
else:
assert_(len(w) == 0)
- def test_result_values(self):
- for nf, rf in zip(self.nanfuncs, self.stdfuncs):
- tgt = [rf(d) for d in _rdat]
- res = nf(_ndat, axis=1)
- assert_almost_equal(res, tgt)
-
def test_allnans(self):
mat = np.array([np.nan]*9).reshape(3, 3)
for f in self.nanfuncs:
@@ -508,24 +459,6 @@ class TestNanFunctions_MeanVarStd(TestCase):
assert_equal(f(mat, axis=axis), np.zeros([]))
assert_(len(w) == 0)
- def test_scalar(self):
- for f in self.nanfuncs:
- assert_(f(0.) == 0.)
-
- def test_matrices(self):
- # Check that it works and that type and
- # shape are preserved
- mat = np.matrix(np.eye(3))
- for f in self.nanfuncs:
- res = f(mat, axis=0)
- assert_(isinstance(res, np.matrix))
- assert_(res.shape == (1, 3))
- res = f(mat, axis=1)
- assert_(isinstance(res, np.matrix))
- assert_(res.shape == (3, 1))
- res = f(mat)
- assert_(np.isscalar(res))
-
class TestNanFunctions_Median(TestCase):