Skip to content

Commit b8ae20e

Browse files
gregorylivschitzjreback
authored andcommitted
BUG:fixed inconsistent behavior of last_valid_index
closes #12800 closes #12834
1 parent e1aa2d9 commit b8ae20e

File tree

4 files changed

+22
-2
lines changed

4 files changed

+22
-2
lines changed

doc/source/whatsnew/v0.18.1.txt

+1-1
Original file line numberDiff line numberDiff line change
@@ -256,7 +256,7 @@ Bug Fixes
256256

257257

258258
- Bug in ``.str`` accessor methods may raise ``ValueError`` if input has ``name`` and the result is ``DataFrame`` or ``MultiIndex`` (:issue:`12617`)
259-
259+
- Bug in ``DataFrame.last_valid_index()`` and ``DataFrame.first_valid_index()`` on empty frames (:issue:`12800`)
260260

261261

262262
- Bug in ``CategoricalIndex.get_loc`` returns different result from regular ``Index`` (:issue:`12531`)

pandas/core/frame.py

+6
Original file line numberDiff line numberDiff line change
@@ -3766,12 +3766,18 @@ def first_valid_index(self):
37663766
"""
37673767
Return label for first non-NA/null value
37683768
"""
3769+
if len(self) == 0:
3770+
return None
3771+
37693772
return self.index[self.count(1) > 0][0]
37703773

37713774
def last_valid_index(self):
37723775
"""
37733776
Return label for last non-NA/null value
37743777
"""
3778+
if len(self) == 0:
3779+
return None
3780+
37753781
return self.index[self.count(1) > 0][-1]
37763782

37773783
# ----------------------------------------------------------------------

pandas/tests/frame/test_timeseries.py

+5
Original file line numberDiff line numberDiff line change
@@ -336,3 +336,8 @@ def test_first_last_valid(self):
336336

337337
index = frame.last_valid_index()
338338
self.assertEqual(index, frame.index[-6])
339+
340+
# GH12800
341+
empty = DataFrame()
342+
self.assertIsNone(empty.last_valid_index())
343+
self.assertIsNone(empty.first_valid_index())

pandas/tests/series/test_timeseries.py

+10-1
Original file line numberDiff line numberDiff line change
@@ -19,7 +19,6 @@
1919

2020

2121
class TestSeriesTimeSeries(TestData, tm.TestCase):
22-
2322
_multiprocess_can_split_ = True
2423

2524
def test_shift(self):
@@ -222,6 +221,7 @@ def test_asof(self):
222221

223222
def test_getitem_setitem_datetimeindex(self):
224223
from pandas import date_range
224+
225225
N = 50
226226
# testing with timezone, GH #2785
227227
rng = date_range('1/1/1990', periods=N, freq='H', tz='US/Eastern')
@@ -304,6 +304,7 @@ def test_getitem_setitem_datetime_tz_pytz(self):
304304
from pytz import timezone as tz
305305

306306
from pandas import date_range
307+
307308
N = 50
308309
# testing with timezone, GH #2785
309310
rng = date_range('1/1/1990', periods=N, freq='H', tz='US/Eastern')
@@ -343,6 +344,7 @@ def test_getitem_setitem_datetime_tz_dateutil(self):
343344
x) # handle special case for utc in dateutil
344345

345346
from pandas import date_range
347+
346348
N = 50
347349
# testing with timezone, GH #2785
348350
rng = date_range('1/1/1990', periods=N, freq='H', tz='US/Eastern')
@@ -372,6 +374,7 @@ def test_getitem_setitem_datetime_tz_dateutil(self):
372374

373375
def test_getitem_setitem_periodindex(self):
374376
from pandas import period_range
377+
375378
N = 50
376379
rng = period_range('1/1/1990', periods=N, freq='H')
377380
ts = Series(np.random.randn(N), index=rng)
@@ -460,6 +463,7 @@ def test_asof_periodindex(self):
460463

461464
def test_asof_more(self):
462465
from pandas import date_range
466+
463467
s = Series([nan, nan, 1, 2, nan, nan, 3, 4, 5],
464468
index=date_range('1/1/2000', periods=9))
465469

@@ -605,6 +609,11 @@ def test_first_last_valid(self):
605609
self.assertIsNone(ser.last_valid_index())
606610
self.assertIsNone(ser.first_valid_index())
607611

612+
# GH12800
613+
empty = Series()
614+
self.assertIsNone(empty.last_valid_index())
615+
self.assertIsNone(empty.first_valid_index())
616+
608617
def test_mpl_compat_hack(self):
609618
result = self.ts[:, np.newaxis]
610619
expected = self.ts.values[:, np.newaxis]

0 commit comments

Comments
 (0)