元素最多两个忽略NaN的数据框

时间:2015-10-08 13:23:51

标签: python-3.x math pandas dataframe

我有两个数据帧(df1和df2),每个数据帧都有相同的行和列。我想逐个元素地取这两个数据帧的最大值。此外,任何元素最大值与数字和NaN的结果应该是数字。到目前为止我实施的方法似乎效率低下:

def element_max(df1,df2):
    import pandas as pd
    cond = df1 >= df2
    res = pd.DataFrame(index=df1.index, columns=df1.columns)
    res[(df1==df1)&(df2==df2)&(cond)]  = df1[(df1==df1)&(df2==df2)&(cond)]
    res[(df1==df1)&(df2==df2)&(~cond)] = df2[(df1==df1)&(df2==df2)&(~cond)]
    res[(df1==df1)&(df2!=df2)&(~cond)] = df1[(df1==df1)&(df2!=df2)]
    res[(df1!=df1)&(df2==df2)&(~cond)] = df2[(df1!=df1)&(df2==df2)]
    return res

还有其他想法吗?谢谢你的时间。

2 个答案:

答案 0 :(得分:12)

您可以使用where来测试您的df与另一个df,其中条件为True,返回df的值,而来自df1的值为false被退回。此外,如果NaN值位于df1,则对fillna(df)的额外调用将​​使用df中的值填充NaN并返回所需的值DF:

In [178]:
df = pd.DataFrame(np.random.randn(5,3))
df.iloc[1,2] = np.NaN
print(df)
df1 = pd.DataFrame(np.random.randn(5,3))
df1.iloc[0,0] = np.NaN
print(df1)

          0         1         2
0  2.671118  1.412880  1.666041
1 -0.281660  1.187589       NaN
2 -0.067425  0.850808  1.461418
3 -0.447670  0.307405  1.038676
4 -0.130232 -0.171420  1.192321
          0         1         2
0       NaN -0.244273 -1.963712
1 -0.043011 -1.588891  0.784695
2  1.094911  0.894044 -0.320710
3 -1.537153  0.558547 -0.317115
4 -1.713988 -0.736463 -1.030797

In [179]:
df.where(df > df1, df1).fillna(df)

Out[179]:
          0         1         2
0  2.671118  1.412880  1.666041
1 -0.043011  1.187589  0.784695
2  1.094911  0.894044  1.461418
3 -0.447670  0.558547  1.038676
4 -0.130232 -0.171420  1.192321

答案 1 :(得分:6)

在最近的pandas版本中,更可读的方法是concat-and-max:

import scipy as sp
import pandas as pd

A = pd.DataFrame([[1., 2., 3.]])
B = pd.DataFrame([[3., sp.nan, 1.]])

pd.concat([A, B]).max(level=0)
# 
#           0    1    2
#      0  3.0  2.0  3.0 
#