查找最近索引值的最快方法

时间:2016-11-01 22:26:40

标签: python performance pandas numpy

考虑时间序列s及其索引tidx

tidx = pd.date_range('2010-12-31', periods=3, freq='M')
s = pd.Series([0, 31, 59], tidx)

如果我想将s用作查找系列并传递日期'2011-02-23',我希望获得最近可用的值。在这种情况下,这将是31

我已经完成了

s.resample('D').ffill().loc['2011-02-23']

31

这可以完成这项工作,但我不得不重新取样整个系列只是为了得到一个值。有什么更合适的方法呢?

3 个答案:

答案 0 :(得分:7)

您可以使用searchsorted -

s[s.index.searchsorted('2011-02-23','right')-1]

有趣的是你打败自己!所以,这里有更多的NumPy进一步提升性能 -

s[s.index.values.searchsorted(np.datetime64('2011-02-23'),'right')-1]

运行时测试 -

In [235]: tidx = pd.date_range('2010-12-31', periods=300, freq='M')
     ...: s = pd.Series(range(300), tidx)
     ...: 

In [236]: s[s.index.searchsorted('2035-03-23','right')-1]
Out[236]: 290

In [237]: s[s.index.values.searchsorted(np.datetime64('2035-03-23'),'right')-1]
Out[237]: 290

In [238]: %timeit s[s.index.searchsorted('2035-03-23','right')-1]
10000 loops, best of 3: 63 µs per loop

In [239]: %timeit s[s.index.values.searchsorted(np.datetime64('2035-03-23'),'right')-1]
10000 loops, best of 3: 46.7 µs per loop

答案 1 :(得分:2)

这是怎么回事?

In [150]: s[s.index <= '2011-02-23'].tail(1)
Out[150]:
2011-01-31    31
Freq: M, dtype: int64

PS只有在索引排序后才会起作用......

答案 2 :(得分:2)

我使用了s.index.get_loc()

docs

它允许查找“最接近”的索引值位置。

s.iloc[s.index.get_loc('2011-02-23', 'ffill')]