ID Period status Flag (Output)
A 2020-10-28 0 1
A 2020-11-28 0 1
A 2020-12-28 0 1
A 2021-01-28 0 1
A 2021-02-28 0 1
A 2021-03-28 0 1
A 2021-04-28 0 1
A 2021-05-28 0 1
A 2021-06-28 1 0
A 2021-07-28 0 0
A 2021-08-28 0 0
A 2021-09-28 0 0
A 2021-10-28 0 0
下面是根据状态列生成标志的简单示例: 例如:对于唯一的 ID-A,为了标记第一行,我检查接下来 12 个月的“状态”列,如果接下来 12 个月内的状态为 1,我会将 O/P 标记为 1。 下面是我的示例代码,它给了我想要的结果,但是从性能角度来看,这对于大量数据(具有接近 100 万个具有不同 ID 的数据)来说效率不高。有没有一种方法可以以更简单、更快的方式进行编码,或者循环是唯一的选择。
df = df1[['ID','Period','status']]
df = df.sort_values(by=['ID','Period']).reset_index(drop=True)
df['flag']=0
default=pd.DataFrame()
j=df['ID'].unique()
k=pd.DataFrame(j,columns=['ID'])
for a,i in k.iterrows():
temp = df[df['ID']==i['ID']]
temp = temp.reset_index(drop=True)
for x,y in temp.iterrows():
if temp.iloc[x+1:x+13,2].sum() >= 1:
temp.loc[x,'flag']=1
else:
temp.loc[x,'flag']=0
default = default.append(temp)
您可以使用
groupby.rolling
:
df['Flag'] = (df
.assign(Period=pd.to_datetime(df['Period']).dt.to_period('M'))
[::-1]
.groupby('ID').rolling(12, on='Period', min_periods=1)
['Flag'].max()[::-1].to_numpy()
)
输出:
ID Period status Flag
0 A 2020-10-28 0 1.0
1 A 2020-11-28 0 1.0
2 A 2020-12-28 0 1.0
3 A 2021-01-28 0 1.0
4 A 2021-02-28 0 1.0
5 A 2021-03-28 0 1.0
6 A 2021-04-28 0 1.0
7 A 2021-05-28 0 1.0
8 A 2021-06-28 1 0.0
9 A 2021-07-28 0 0.0
10 A 2021-08-28 0 0.0
11 A 2021-09-28 0 0.0
12 A 2021-10-28 0 0.0