Pandas - Python: Apply() and if/then logic
我有以下数据帧:
1 2 3 | example = pd.DataFrame({"dirr":[1,0,-1,-1,1,-1,0], "value": [125,130,80,8,150,251,18], "result":[np.NaN for _ in range(7)]}) |
我想使用cummin()和cummax()对其执行以下操作:
1 2 3 4 | example["result"].apply(lambda x : x= example["value"].cummax() if example["dirr"]==1 else x= example["value"].cummin() if example["dirr"]==-1 else x= NaN if if example["dirr"]==0 ) |
这是返回:
有人能帮我把那个弄直吗?
即预期产量:
1 2 3 | example = pd.DataFrame({"dirr":[1,0,-1,-1,1,-1,0], "value": [125,130,80,8,150,251,18], "result":[125, NaN, 80, 8, 150, 8, NaN]}) |
编辑:
因此,根据@su79eu7k的回答,以下功能将起作用:
1 2 3 4 5 6 7 | def calc(x): if x['dirr'] == 1: return np.diag(example["value"].cummax()) elif x['dirr'] == -1: return np.diag(example["value"].cummin()) else: return np.nan |
我应该能够将它推到lambda中,但仍然由于语法错误而受阻…我还是看不见?
1 2 3 4 | example["result"]=example.apply(lambda x : np.diag(x["value"].cummax()) if x["dirr"]==1 else np.diag(x["value"].cummin()) if x["dirr"]==-1 else NaN if x["dirr"]==0 ) |
最后一个小动作,你们会非常感激。
我认为@3novak的解决方案简单快速。但如果您真的想使用
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 | def calc(x): if x['dirr'] == 1: return example["value"].cummax() elif x['dirr'] == -1: return example["value"].cummin() else: return np.nan example['result'] = np.diag(example.apply(calc, axis=1)) print example dirr result value 0 1 125.0 125 1 0 NaN 130 2 -1 80.0 80 3 -1 8.0 8 4 1 150.0 150 5 -1 8.0 251 6 0 NaN 18 |
我认为使用单独的行而不是应用程序是最有意义的。如果确实使用了apply函数,那么应该创建一个单独的函数并传递它,而不是生成一个三行lambda。
1 2 3 4 5 6 7 8 9 10 11 12 13 14 | example.loc[example['dirr'] == 1, 'result'] = \ example.loc[example['dirr'] == 1, 'value'].cummax() example.loc[example['dirr'] == -1, 'result'] = \ example.loc[example['dirr'] == -1, 'value'].cummin() >>> example dirr result value 0 1 125.0 125 1 0 NaN 130 2 -1 80.0 80 3 -1 8.0 8 4 1 150.0 150 5 -1 8.0 251 6 0 NaN 18 |
下面交替使用
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 | current_max = 0 current_min = 9999 def func(df): global current_max global current_min if df['dirr'] == 1: current_max = max(current_max, df['value']) return current_max elif df['dirr'] == -1: current_min = min(current_min, df['value']) return current_min else: return np.nan example['result'] = example.apply(func, axis=1) |
全麻木
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 | v = example.value.values d = example.dirr.values mx = np.maximum.accumulate(v) mn = np.minimum.accumulate(v) example['result'] = np.where(d == 1, mx, np.where(d == -1, mn, np.nan)) example dirr result value 0 1 125.0 125 1 0 NaN 130 2 -1 80.0 80 3 -1 8.0 8 4 1 150.0 150 5 -1 8.0 251 6 0 NaN 18 |
计时