返回每个月的最后日期和价值(以熊猫为单位)

时间:2018-07-31 03:16:41

标签: python python-3.x pandas

我有熊猫的df,有每日数据。我想返回每个月的最后一个值。我以为简单的解决方案将是.resample("M").apply(lambda ser: ser.iloc[-1,]),但是似乎resample实际上是在计算月结束日期,而不是返回该月出现的实际日期。这是预期的行为吗? MWE:

import pandas as pd
import numpy as np
df = pd.Series(np.arange(100), index=pd.date_range(start="2000-01-02", periods=100)).to_frame()
df.sort_index().resample("M").apply(lambda ser: ser.iloc[-1,])
#             0
#2000-01-31  29
#2000-02-29  58
#2000-03-31  89
#2000-04-30  99

df中出现的最后一个日期是2000-04-10

2 个答案:

答案 0 :(得分:2)

您可能需要查看groupby + tail

df.groupby(df.index.month).tail(1)
Out[18]: 
             0
2000-01-31  29
2000-02-29  58
2000-03-31  89
2000-04-10  99

答案 1 :(得分:2)

通过将resampleoffset M一起使用,您可以 下采样 ,直到日历月底(请参见偏移量的链接文档),然后传递函数。因此,您的索引将始终是该月的最后一天,这确实是预期的行为。您正在应用的函数(lambda ser: ser.iloc[-1,])只是说:对于这一天结束的日历日期,原始数据中找到的最后一个值是什么。

例如,您还可以使用偏移量MS而不是M重新采样到月份开始,结果将是相同的,除了索引将是 first 日历月的一天,而不是最后一天:

# Resample to month end, as you had originally:
>>> df.sort_index().resample("M").apply(lambda ser: ser.iloc[-1,])
             0
2000-01-31  29
2000-02-29  58
2000-03-31  89
2000-04-30  99

# Resample to month start: same data, except index is month start instead of month end
>>> df.sort_index().resample("MS").apply(lambda ser: ser.iloc[-1,])
             0
2000-01-01  29
2000-02-01  58
2000-03-01  89
2000-04-01  99

正如Wen指出的那样,如果您只想显示数据中的实际最后日期,最好使用groupby。 重采样在要将数据上采样或下采样到不同时间频率时很有用 ,而不是从原始时间频率中选择真实数据

>