这是我的数据框:
import pandas as pd
df = pd.DataFrame({
'a': [10, 20, 30, 1, 20, 3, 4],
'b': [30, 10, 9, 21, 24, 31, 29],
'c': [True, True, False, False, False, True, True]
})
预期输出正在创建列
d
:
a b c d
0 10 30 True NaN
1 20 3 True 10
2 30 11 True 20
3 1 25 False NaN
4 20 24 False NaN
5 3 31 True NaN
6 4 29 True 30
首先选择
b
中的值,其c
为True
。我从第1
行解释这个过程,因为它更容易理解。
b
中的值为3,则应检查其上方的所有值。应选择 a
中大于 3 的最近值。所以选择了10。
对于行号
2
,该值为 11。a
中比该行最接近的值是 20。
对于第 3 行和第 4 行,因为
c
是 False
。应选择 NaN
。
对于第
5
行,由于 a
中没有大于 31 的先前值,因此选择 NaN
。
对于第
6
行,a
中大于 29 的最接近值是 30。
这是我到目前为止所尝试过的。它没有给我输出。我认为我采取的方法可能是正确的。
t = df['a'].to_numpy()
h = df['b'].to_numpy()
m2 = t < h[:, None]
df['d'] = np.nanmax(np.where(m2, t, np.nan), axis=1)
要在“a”列中查找大于“b”列中当前值的最近值(仅当“c”为 True 时),您可以使用矢量化方法或简单的循环解决方案。
def find_previous_greater(df):
result = pd.Series(index=df.index, dtype=float)
for idx in df[df['c']].index:
prev_vals = df.loc[:idx-1, 'a']
if len(prev_vals) > 0:
greater_vals = prev_vals[prev_vals > df.loc[idx, 'b']]
if len(greater_vals) > 0:
result[idx] = greater_vals.iloc[-1]
return result
df['d'] = find_previous_greater(df)
这给了我这个输出: