2017-08-30 227 views
0

由于my previous question的延伸,我想采取类似下面的一个数据帧,并找到正确的行,从该从C列提取数据,并将其放置到基于以下标准列D根据计算值从Pandas DataFrame中的行中查找数据?

  1. B_new = 2*A_old -B_old即,新行需要有一个B等于旧行的以下结果:2*A - B
  2. 其中A是相同的,即。新行中的A应该与旧行具有相同的值。
  3. 没有发现任何值应使用NaN结果

代码:

import pandas as pd 
a = [2,2,2,3,3,3,3] 
b = [1,2,3,1,3,4,5] 
c = [0,1,2,3,4,5,6] 

df = pd.DataFrame({'A': a , 'B': b, 'C':c}) 
print(df) 

    A B C 
0 2 1 0 
1 2 2 1 
2 2 3 2 
3 3 1 3 
4 3 3 4 
5 3 4 5 
6 3 5 6 

所需的输出:

A B C D 
0 2 1 0 2.0 
1 2 2 1 1.0 
2 2 3 2 0.0 
3 3 1 3 6.0 
4 3 3 4 4.0 
5 3 4 5 NaN 
6 3 5 6 3.0 

基于在my previous question的解决方案,我想出了一种使用for循环移动每个唯一值A的方法:

for i in df.A.unique(): 
    mapping = dict(df[df.A==i][['B', 'C']].values) 
    df.loc[df.A==i,'D'] = (2 * df[df.A==i]['A'] - df[df.A==i]['B']).map(mapping) 

但是,这看起来很笨重,我怀疑有一个更好的方法,不使用for循环,从我以前的经验来看,这往往是缓慢的。

问题: 什么是在DataFrame中完成数据传输的最快方法?

回答

1

你可以

In [370]: (df[['A', 'C']].assign(B=2*df.A - df.B) 
      .merge(df, how='left', on=['A', 'B']) 
      .assign(B=df.B) 
      .rename(columns={'C_x': 'C', 'C_y': 'D'})) 
Out[370]: 
    A C B D 
0 2 0 1 2.0 
1 2 1 2 1.0 
2 2 2 3 0.0 
3 3 3 1 6.0 
4 3 4 3 4.0 
5 3 5 4 NaN 
6 3 6 5 3.0 

详情:

In [372]: df[['A', 'C']].assign(B=2*df.A - df.B) 
Out[372]: 
    A C B 
0 2 0 3 
1 2 1 2 
2 2 2 1 
3 3 3 5 
4 3 4 3 
5 3 5 2 
6 3 6 1 

In [373]: df[['A', 'C']].assign(B=2*df.A - df.B).merge(df, how='left', on=['A', 'B']) 
Out[373]: 
    A C_x B C_y 
0 2 0 3 2.0 
1 2 1 2 1.0 
2 2 2 1 0.0 
3 3 3 5 6.0 
4 3 4 3 4.0 
5 3 5 2 NaN 
6 3 6 1 3.0 
相关问题