From 010741f3eb4ec6f05edc4168549ea8b05cb018fc Mon Sep 17 00:00:00 2001 From: unutbu Date: Tue, 2 Dec 2014 19:54:42 -0500 Subject: [PATCH] BUG: Fixed ValueError raised by cummin/cummax when datetime64 Series contains NaT. (:issue:`8965`) --- doc/source/whatsnew/v0.15.2.txt | 1 + pandas/core/generic.py | 14 ++++++--- pandas/tests/test_series.py | 56 +++++++++++++++++++++++++++++++++ 3 files changed, 66 insertions(+), 5 deletions(-) diff --git a/doc/source/whatsnew/v0.15.2.txt b/doc/source/whatsnew/v0.15.2.txt index 929471acb3105..0a0bed826abba 100644 --- a/doc/source/whatsnew/v0.15.2.txt +++ b/doc/source/whatsnew/v0.15.2.txt @@ -166,3 +166,4 @@ Bug Fixes not lexically sorted or unique (:issue:`7724`) - BUG CSV: fix problem with trailing whitespace in skipped rows, (:issue:`8679`), (:issue:`8661`) - Regression in ``Timestamp`` does not parse 'Z' zone designator for UTC (:issue:`8771`) +- Fixed ValueError raised by cummin/cummax when datetime64 Series contains NaT. (:issue:`8965`) diff --git a/pandas/core/generic.py b/pandas/core/generic.py index 52f37ee24f69a..b948ceb9b6b88 100644 --- a/pandas/core/generic.py +++ b/pandas/core/generic.py @@ -4112,13 +4112,17 @@ def func(self, axis=None, dtype=None, out=None, skipna=True, axis = self._get_axis_number(axis) y = _values_from_object(self).copy() - if not issubclass(y.dtype.type, (np.integer, np.bool_)): + + if skipna and issubclass(y.dtype.type, + (np.datetime64, np.timedelta64)): + result = accum_func(y, axis) + mask = isnull(self) + np.putmask(result, mask, pd.tslib.iNaT) + elif skipna and not issubclass(y.dtype.type, (np.integer, np.bool_)): mask = isnull(self) - if skipna: - np.putmask(y, mask, mask_a) + np.putmask(y, mask, mask_a) result = accum_func(y, axis) - if skipna: - np.putmask(result, mask, mask_b) + np.putmask(result, mask, mask_b) else: result = accum_func(y, axis) diff --git a/pandas/tests/test_series.py b/pandas/tests/test_series.py index c4c2eebacb0e9..df48c5e62a9b6 100644 --- a/pandas/tests/test_series.py +++ b/pandas/tests/test_series.py @@ -2309,6 +2309,62 @@ def test_cummax(self): self.assert_numpy_array_equal(result, expected) + def test_cummin_datetime64(self): + s = pd.Series(pd.to_datetime( + ['NaT', '2000-1-2', 'NaT', '2000-1-1', 'NaT', '2000-1-3'])) + + expected = pd.Series(pd.to_datetime( + ['NaT', '2000-1-2', 'NaT', '2000-1-1', 'NaT', '2000-1-1'])) + result = s.cummin(skipna=True) + self.assert_series_equal(expected, result) + + expected = pd.Series(pd.to_datetime( + ['NaT', '2000-1-2', '2000-1-2', '2000-1-1', '2000-1-1', '2000-1-1'])) + result = s.cummin(skipna=False) + self.assert_series_equal(expected, result) + + def test_cummax_datetime64(self): + s = pd.Series(pd.to_datetime( + ['NaT', '2000-1-2', 'NaT', '2000-1-1', 'NaT', '2000-1-3'])) + + expected = pd.Series(pd.to_datetime( + ['NaT', '2000-1-2', 'NaT', '2000-1-2', 'NaT', '2000-1-3'])) + result = s.cummax(skipna=True) + self.assert_series_equal(expected, result) + + expected = pd.Series(pd.to_datetime( + ['NaT', '2000-1-2', '2000-1-2', '2000-1-2', '2000-1-2', '2000-1-3'])) + result = s.cummax(skipna=False) + self.assert_series_equal(expected, result) + + def test_cummin_timedelta64(self): + s = pd.Series(pd.to_timedelta( + ['NaT', '2 min', 'NaT', '1 min', 'NaT', '3 min', ])) + + expected = pd.Series(pd.to_timedelta( + ['NaT', '2 min', 'NaT', '1 min', 'NaT', '1 min', ])) + result = s.cummin(skipna=True) + self.assert_series_equal(expected, result) + + expected = pd.Series(pd.to_timedelta( + ['NaT', '2 min', '2 min', '1 min', '1 min', '1 min', ])) + result = s.cummin(skipna=False) + self.assert_series_equal(expected, result) + + def test_cummax_timedelta64(self): + s = pd.Series(pd.to_timedelta( + ['NaT', '2 min', 'NaT', '1 min', 'NaT', '3 min', ])) + + expected = pd.Series(pd.to_timedelta( + ['NaT', '2 min', 'NaT', '2 min', 'NaT', '3 min', ])) + result = s.cummax(skipna=True) + self.assert_series_equal(expected, result) + + expected = pd.Series(pd.to_timedelta( + ['NaT', '2 min', '2 min', '2 min', '2 min', '3 min', ])) + result = s.cummax(skipna=False) + self.assert_series_equal(expected, result) + def test_npdiff(self): raise nose.SkipTest("skipping due to Series no longer being an " "ndarray")