熊猫:如果它不存在,获得系列或者nan的唯一值

Khr*_*ris 5 python pandas

我在数据帧上做了一些更复杂的操作,我比较了可以在帧中任何位置的两行.

这是一个例子:

import pandas as pd
import numpy as np

D = {'A':['a','a','c','e','e','b','b'],'B':['c','f','a','b','d','a','e']\
 ,'AW':[1,2,3,4,5,6,7],'BW':[10,20,30,40,50,60,70]}
P = pd.DataFrame(D)
P = P.sort_values(['A','B'])
P['AB'] = P.A+'_'+P.B
P['AWBW'] = P.AW+P.BW
Run Code Online (Sandbox Code Playgroud)

现在我在做什么在这里,我在字符串的配对AB,例如a_c我打电话AB.我也有反向配对c_a.我总结了数字AWBW每个配对,称为AWBW.

现在我想从值中减去求和值,a_c并对c_a存在两个变量的每个字符串配对执行相同的操作.所有其他值应该是NaN,所以我的结果应如下所示:

   A  AW  B  BW   AB  AWBW  RowDelta
0  a   1  c  10  a_c    11     -22.0
1  a   2  f  20  a_f    22       NaN
5  b   6  a  60  b_a    66       NaN
6  b   7  e  70  b_e    77      33.0
2  c   3  a  30  c_a    33      22.0
3  e   4  b  40  e_b    44     -33.0
4  e   5  d  50  e_d    55       NaN
Run Code Online (Sandbox Code Playgroud)

我几乎已经解决了这个问题的方法,但是我遇到了一个问题.

到目前为止,这是我的解决方案:

for i,row in P.iterrows():
  P.ix[i,'RowDelta'] = row['AWBW']\
   - P[(P['A'] == row.AB[2]) & (P['B'] == row.AB[0])]['AWBW'].get(0,np.nan)
Run Code Online (Sandbox Code Playgroud)

问题是P[(P['A'] == row.AB[2]) & (P['B'] == row.AB[0])]['AWBW']返回一个空的系列,或者只有一个元素,其索引是可变的.

现在该series.get方法解决了NaN当系列为空但是想要一个确定的索引值时返回的问题,在这种情况下我使用0,但我无法获得动态索引.

我不能这样做

T = P[(P['A'] == row.AB[2]) & (P['B'] == row.AB[0])]['AWBW']
T.get(T.index[0],np.nan)
Run Code Online (Sandbox Code Playgroud)

因为如果系列为空则没有索引,这会导致执行时出错T.index[0].我尝试使用也是如此iloc.

有没有办法动态获取一个系列的未知一个索引,如果它有一个元素(并且从不多于一个),同时处理一个空系列的情况?

Khr*_*ris 2

感谢piRSquared为我指明了解决方案的正确方向:

AB = P.AB.str.split('_', expand=True)
AB = AB.merge(AB, left_on=[0, 1], right_on=[1, 0],how='inner')[[0,1]]
AB = AB.merge(P,left_on=[0,1], right_on=['A','B'])[['A','AW','B','BW']]
AB = AB.merge(P,left_on=['A','B'], right_on=['B','A'])[['AW_x','BW_x','AW_y','BW_y','AB']]
AB['RowDelta'] = AB.AW_y+AB.BW_y-AB.AW_x-AB.BW_x
P = P.merge(AB[['AB','RowDelta']],on='AB',how='outer')
Run Code Online (Sandbox Code Playgroud)

也许它可以变得更短或更漂亮,它肯定有效。