给出数据框
import pandas as pd
df = pd.DataFrame({
'transformed': ['left', 'right', 'left', 'right'],
'left_f': [1, 2, 3, 4],
'right_f': [10, 20, 30, 40],
'left_t': [-1, -2, -3, -4],
'right_t': [-10, -20, -30, -40],
})
我想创建两个新列,根据left_*
的内容从right_*
或transformed
中选取:
df['transformed_f'] = df['right_f'].where(
df['transformed'] == 'right',
df['left_f']
)
df['transformed_t'] = df['right_t'].where(
df['transformed'] == 'right',
df['left_t']
)
我得到了预期的结果
df
# transformed left_f right_f left_t right_t transformed_f transformed_t
# 0 left 1 10 -1 -10 1 -1
# 1 right 2 20 -2 -20 20 -20
# 2 left 3 30 -3 -30 3 -3
# 3 right 4 40 -4 -40 40 -40
但是,当我尝试执行一次操作时,会得到包含NaN
值的意外结果
df[['transformed_f', 'transformed_t']] = df[['right_f', 'right_t']].where(
df['transformed'] == 'right',
df[['left_f', 'left_t']]
)
df
# transformed left_f right_f left_t right_t transformed_f transformed_t
# 0 left 1 10 -1 -10 NaN NaN
# 1 right 2 20 -2 -20 20.0 -20.0
# 2 left 3 30 -3 -30 NaN NaN
# 3 right 4 40 -4 -40 40.0 -40.0
是否可以同时在多列上使用df.where()
?
答案 0 :(得分:4)
您接近了,只需在切片中添加.values
或.to_numpy()
使其成为NDarray
:
每个文档:
other:标量,NDFrame或可调用 cond为False的条目将替换为其他条目的对应值。如果other是可调用的,则它在NDFrame上计算,并应返回标量或NDFrame。可调用对象不得更改输入NDFrame(尽管pandas不会对其进行检查)。
因此,当您直接输入数据帧的切片时,索引(列名)不匹配,因此它不会更新df,当您传递.values
时,它将忽略索引并添加值。
df[['transformed_f', 'transformed_t']]=(df[['right_f', 'right_t']].
where(df['transformed'] == 'right',df[['left_f', 'left_t']].values))
print(df)
transformed left_f right_f left_t right_t transformed_f transformed_t
0 left 1 10 -1 -10 1 -1
1 right 2 20 -2 -20 20 -20
2 left 3 30 -3 -30 3 -3
3 right 4 40 -4 -40 40 -40