在滚动功能之后保持最高结果但没有相交的窗口

时间:2014-12-11 08:36:17

标签: python pandas

我正在寻找一种在Pandas中执行滚动功能的方法,并保留一个特定值,例如最高或最低值,然后删除与该范围相交的所有其他窗口。

想象一下,例如一年的温度测量,你想知道已经发生的最温暖的20天。绝对最温暖很容易,执行滚动功能并对结果进行排序。但考虑到温度如何变化的性质,第二个,第三个等可能是同一个时期,窗口只有一天的变化。这就是我想要避免的,因此最终只能得到独特的,不相交的句号。

我找到了下面列出的一个解决方法,但它涉及循环,将结果存储在列表中并重新创建DataFrame,这远非花哨。所以我很好奇是否有人知道处理这些情况的更多Pythonic方式。

可以使用以下内容创建示例数据:

window = 20

end = pd.DatetimeIndex(start='2014-01-01', end='2014-12-31', freq='D')
begin = end.shift(-(window - 1))

df = pd.DataFrame({'begin': begin,
                   'end': end,
                   'values': np.sin(np.linspace(-np.pi, np.pi, len(begin))) * 10.})

df['values'] = pd.rolling_mean(df['values'], window)
df = df.dropna()

这给出了一年的虚拟数据减去由于窗口中缺少值而丢失的前19天。

我的方法如下:

# sort the DataFrame so the 'to keep' values are at the beginning, in this case highest
# 'values' first. But an alternative way of ordering could be used of course.

df.sort('values', ascending=False, inplace=True)

# a list to store rows
keep = []

# loop until there are no rows left in the DataFrame
while len(df) > 0:

    # select the top row
    toprow = df.iloc[0]

    # store it
    keep.append(toprow)

    # get the range of the tow
    end = toprow.end
    begin = toprow.begin

    # boolean mask for all ranges intersecting the selected range
    before = (df.end >= begin) & (df.end <= end)
    after = (df.begin >= begin) & (df.begin <= end)

    # remove all other values intersecting with the range
    df = df[~(before | after)]

# merge the stored rows (Series) to a DataFrame
df = pd.concat(keep, axis=1).T
df.set_index(['begin', 'end'], inplace=True)
df.head()

结果是:

                         values
begin      end                 
2014-09-21 2014-10-10  9.950167
2014-10-11 2014-10-30  9.392147
2014-09-01 2014-09-20  9.334021
2014-10-31 2014-11-19  7.725809
2014-08-12 2014-08-31  7.616417

因为我使用正弦作为虚拟数据,所以第二高的窗口就在最高的旁边,等等。

不,这应该适用于熊猫吗?它导致了我的错误:

del df[~(before | after)]

0 个答案:

没有答案