我有一个数据框架(df),其中一列('bestcol')包含表中其他列的索引。我想抓住被"bestcol"引用的列,将其四舍五入,并使用该信息创建一个新列(参见下表中的粗略示例,其中bestcol = 1指Val1, 2指Val2, 3指Val3)。
<表类>
Val1
Val2
Val3
bestcol
最后
tbody><<tr>1.1 2.1 3.1 1 1.0 11.122.1 33.1 2 22.0 111.1222.1 333.1 3 333.0 表类>
您可以使用numpy
索引:
row = np.arange(len(df))
col = df['bestcol'].values - 1
x = df.filter(like='Val').values # or df.iloc[:, :3].values
df['Final'] = np.round(x[row, col])
输出:
>>> df
Val1 Val2 Val3 bestcol Final
0 1.1 2.1 3.1 1 1.0
1 11.1 22.1 33.1 2 22.0
2 111.1 222.1 333.1 3 333.0
5_000_000行100列的性能:
M = 5_000_000
N = 100
x = np.random.uniform(1, 500, (M, N))
row = np.arange(M)
col = np.random.randint(1, N+1, M) - 1
%timeit np.round(x[row, col])
75.5 ms ± 388 µs per loop (mean ± std. dev. of 7 runs, 10 loops each)
我使用嵌套的np.where
来处理三个条件,然后使用np.round
。
df['Final'] = np.round(np.where(df.bestcol == 1, df.Val1, np.where(df.bestcol == 2, df.Val2, df.Val3)), 0)
由于您的bestcol
包含实际列的有序顺序位置,您可以应用numpy.diag
:
df['Final'] = np.round(np.diag(df[df.columns[:-1]]))
1 2 3 bestcol Final
0 1.1 2.1 3.1 1 1.0
1 11.1 22.1 33.1 2 22.0
2 111.1 222.1 333.1 3 333.0
一个简单快速的python方法:
import pandas as pd
df = pd.DataFrame({'Val1': [1.1, 11.1, 111.1],
'Val2': [2.1, 22.1, 222.1],
'Val3': [3.1, 33.1, 333.1],
'bestcol': [1, 2, 3],
})
df['Final'] = [round(df[['Val1', 'Val2', 'Val3']].iloc[i, p])
for i, p in enumerate(df.bestcol.sub(1).tolist())]
print(df)
结果
Val1 Val2 Val3 bestcol Final
0 1.1 2.1 3.1 1 1
1 11.1 22.1 33.1 2 22
2 111.1 222.1 333.1 3 333
try this:
df['Final'] = df.values[df.index, df.bestcol-1].round(0)
print(df)
>>>
Val1 Val2 Val3 bestcol Final
0 1.1 2.1 3.1 1 1.0
1 11.1 22.1 33.1 2 22.0
2 111.1 222.1 333.1 3 333.0