我有一个pandas日期框架df
,其索引为每日DatetimeIndex
,附加列为historical_sales
。
如果我们想过滤历史数据大于大数的过去几天,比如说200
,那就够了:
df.loc[df['historical_sales'>200]]
我想知道,如果我们想要在销售前后的5天内和之后的5天内探讨销售模式,那该怎么办呢? 200?
非常感谢。
答案 0 :(得分:1)
我认为您不需要按列表推导获取所有索引值,然后按loc
选择。
还必须使用numpy.concatenate
与numpy.unique
一起加入所有索引以删除重复项。
np.random.seed(100)
rng = pd.date_range('2017-04-03', periods=20)
df = pd.DataFrame({'historical_sales': np.random.choice([100,200,300], size=20)}, index=rng)
print (df)
historical_sales
2017-04-03 100
2017-04-04 100
2017-04-05 100
2017-04-06 300
2017-04-07 300
2017-04-08 100
2017-04-09 300
2017-04-10 200
2017-04-11 300
2017-04-12 300
2017-04-13 300
2017-04-14 300
2017-04-15 200
2017-04-16 100
2017-04-17 100
2017-04-18 100
2017-04-19 100
2017-04-20 300
2017-04-21 100
2017-04-22 200
idxmask = df.index[df['historical_sales']>200]
print (idxmask)
DatetimeIndex(['2017-04-06', '2017-04-07', '2017-04-09', '2017-04-11',
'2017-04-12', '2017-04-13', '2017-04-14', '2017-04-20'],
dtype='datetime64[ns]', freq=None)
#in real data change 1 to 5 for 5 days
temp_index = [df.loc[timestamp - pd.Timedelta(1, unit='d') :
timestamp + pd.Timedelta(1, unit='d')].index for timestamp in idxmask]
idx = np.unique(np.concatenate(temp_index))
df1 = df.loc[idx]
print (df1)
historical_sales
2017-04-05 100
2017-04-06 300
2017-04-07 300
2017-04-08 100
2017-04-09 300
2017-04-10 200
2017-04-11 300
2017-04-12 300
2017-04-13 300
2017-04-14 300
2017-04-15 200
2017-04-19 100
2017-04-20 300
2017-04-21 100
答案 1 :(得分:0)
您可能希望进行范围切片:http://pandas.pydata.org/pandas-docs/stable/indexing.html#selection-by-position
应该看起来像这样(代码是伪代码):
great_sales_df = df.loc[df['historical_sales'>200]]
for sale in great_sales_df:
sales_date = great_sales_df["date"]
sales_before = sales_date + pd.DateOffset(-5)
sales_after = sales_date + pd.DateOffset(+5)
pattern_df = df.iloc[sales_before:sales_after]
此代码不起作用,但我认为方向是正确的。
答案 2 :(得分:0)
为了清楚起见,我添加了一个new
列,对于感兴趣的行设置为1。为了便于验证,在下面的代码中,窗口日期的数量保持为1而不是5,
import pandas as pd
import numpy as np
from datetime import datetime, timedelta
df = pd.DataFrame(data=np.random.rand(51),index=pd.date_range('2015-04-20','2015-06-09'),columns=['A'])
idx = df[df.A >0.5].index
df["new"] = 0
for date in idx:
current_date = date.to_pydatetime()
start = current_date - timedelta(days=1)
end = current_date + timedelta(days=1)
df.loc[start:current_date]["new"] = 1
df.loc[current_date:end]["new"] = 1
print(df)
答案 3 :(得分:0)
当我需要在前后处理行时,我只需执行一次移位。
df['preceeding_5th_day'] = df['historical_sales'].shift(5)
df['following_5th_day'] = df['historical_sales'].shift(-5)
然后,您可以简单地进行检查并执行
df.loc[df['historical_sales'>200]]
然后,所选行还将包含有关第5天之前和之后的列。这种方式很简单。