我有一个问题,它延伸自Pandas: conditional rolling count。 我想在数据帧中创建一个新列,反映满足多个条件的行的累计计数。
使用来自stackoverflow 25119524的以下示例和代码:
import pandas as pd
l1 =["1", "1", "1", "2", "2", "2", "2", "2"]
l2 =[1, 2, 2, 2, 2, 2, 2, 3]
l3 =[45, 25, 28, 70, 95, 98, 120, 80]
cowmast = pd.DataFrame(list(zip(l1, l2, l3)))
cowmast.columns =['Cow', 'Lact', 'DIM']
def rolling_count(val):
if val == rolling_count.previous:
rolling_count.count +=1
else:
rolling_count.previous = val
rolling_count.count = 1
return rolling_count.count
rolling_count.count = 0 #static variable
rolling_count.previous = None #static variable
cowmast['xmast'] = cowmast['Cow'].apply(rolling_count) #new column in dataframe
cowmast
输出每头奶牛的乳腺炎次数(xmast)。
奶牛 泌乳天数 DIM xmast 0 1 1 45 1 1 1 2 25 2 2 1 2 28 3 3 2 2 70 1 4 2 2 95 2 5 2 2 98 3 6 2 2 120 4 7 2 3 80 5对于每头奶牛(cow)的泌乳过程(Lact),我想要在每行之间的天数(DIM)大于7时重新开始计数并增加计数。
为了重置每头奶牛(cow)的每个泌乳过程(Lact)的计数,并仅在满足多个条件时才进行递增,我使用了以下代码。
def count_consecutive_items_n_cols(df, col_name_list, output_col):
cum_sum_list = [
(df[col_name] != df[col_name].shift(1)).cumsum().tolist() for col_name in col_name_list
]
df[output_col] = df.groupby(
["_".join(map(str, x)) for x in zip(*cum_sum_list)]
).cumcount() + 1
return df
count_consecutive_items_n_cols(cowmast, ['Cow', 'Lact'], ['Lxmast'])
产生以下输出:
奶牛 泌乳期 产后天数 乳房发炎次数 上次发炎时间 调整后次数 0 1 1 45 1 1 1 1 2 25 2 1 2 1 2 28 3 2 3 2 2 70 1 1 4 2 2 95 2 2 5 2 2 98 3 2 6 2 2 120 4 3 7 2 3 80 5 1我希望了解如何在累计计数中添加另一个条件,该条件考虑了乳房炎症事件之间的时间差(相同泌乳期内的奶牛行之间的DIM差异)。 如果相同奶牛和泌乳期内行之间的DIM差小于7,则计数不应递增。
我要查找的输出在下面的表格中称为“调整后次数”。
奶牛 泌乳期 产后天数 乳房发炎次数 上次发炎时间 调整后次数 0 1 1 45 1 1 1 1 1 2 25 2 1 1 2 1 2 28 3 2 1 3 2 2 70 1 1 1 4 2 2 95 2 2 2 5 2 2 98 3 3 2 6 2 2 120 4 4 3 7 2 3 80 5 1 1在上述示例中,对于奶牛1泌乳期2,当DIM从25到28时,计数未递增,因为两个事件之间的差小于7天。 当奶牛2泌乳期2从95到98时同样如此。 对于较大的增量70到95和98到120,计数会增加。
谢谢您的帮助。
John