【问题标题】:How to compress dataframe by removing columns that contains 'NaN' value in between columns that has a value?如何通过删除具有值的列之间包含“NaN”值的列来压缩数据帧?
【发布时间】:2019-06-07 13:14:19
【问题描述】:

我目前正在关注答案here。它主要工作,但是当我查看整个数据框时,我看到在包含值的列之间存在包含“NaN”值的列。

例如,我不断得到这样的结果:

     ID | 0  | 1  |   2  |  3   | 4   | 5  | 6  |  7   |  8   | 9
300 1001|1001|1002|  NaN | NaN  | NaN |1001|1002|  NaN | NaN  | NaN   
301 1010|1010|NaN |  NaN | 1000 | 2000|1234| NaN|  NaN | 1213 | 1415
302 1100|1234|5678| 9101 | 1121 | 3141|2345|6789| 1011 | 1617 | 1819
303 1000|2001|9876|  NaN | NaN  | NaN |1001|1002|  NaN | NaN  | NaN  

有没有办法删除那些包含 NaN 的单元格,这样输出会是这样的:

     ID | 0  | 1  |   2  |  3   | 4   | 5  | 6  |  7   |  8   | 9
300 1001|1001|1002|  1001| 1002 | NaN |NaN | NaN|  NaN | NaN  | NaN   
301 1010|1010|1000|  2000| 1234 | 1213|1415| NaN|  NaN | NaN  | NaN
302 1100|1234|5678|  9101| 1121 | 3141|2345|6789| 1011 | 1617 | 1819
303 1000|2001|9876|  1001| 1002 | NaN |NaN |NaN |  NaN | NaN  | NaN 

【问题讨论】:

    标签: python pandas dataframe nan


    【解决方案1】:

    pd.DataFrame.iterrowspd.concat 一起使用:

    import pandas as pd
    
    df[df.columns] = pd.concat([s.dropna().reset_index(drop=True) for i,s in df.iterrows()], 1).T
    

    输出:

             ID     0     1     2     3     4     5     6     7     8     9
    0  300 1001  1001  1002  1001  1002   NaN   NaN   NaN   NaN   NaN   NaN
    1  301 1010  1010  1000  2000  1234  1213  1415   NaN   NaN   NaN   NaN
    2  302 1100  1234  5678  9101  1121  3141  2345  6789  1011  1617  1819
    3  303 1000  2001  9876  1001  1002   NaN   NaN   NaN   NaN   NaN   NaN
    

    【讨论】:

    • 啊,我没想到会这样截断它......很好
    【解决方案2】:

    只需按关键字np.isnan对每一行进行排序

    import pandas as pd
    import numpy as np
    raw = [ [1,2,np.nan,3,np.nan],
            [1,np.nan,3,2,7]]
    original = pd.DataFrame(raw)
    s = original.apply(lambda x:pd.Series(sorted(x,key=np.isnan)),axis=1)
    print(s)
    

    【讨论】:

      【解决方案3】:

      如果性能很重要,请使用justify

      df = pd.DataFrame(justify(df.to_numpy(), invalid_val=np.nan), 
                        index=df.index, 
                        columns=df.columns)
      print (df)
               ID       0       1       2       3       4       5       6       7  \
      300  1001.0  1001.0  1002.0  1001.0  1002.0     NaN     NaN     NaN     NaN   
      301  1010.0  1010.0  1000.0  2000.0  1234.0  1213.0  1415.0     NaN     NaN   
      302  1100.0  1234.0  5678.0  9101.0  1121.0  3141.0  2345.0  6789.0  1011.0   
      303  1000.0  2001.0  9876.0  1001.0  1002.0     NaN     NaN     NaN     NaN   
      
                8       9  
      300     NaN     NaN  
      301     NaN     NaN  
      302  1617.0  1819.0  
      303     NaN     NaN  
      

      如果第一列应该是非数字或可能的缺失值,则解决方案适用于没有第一列的所有列,然后由insert 添加第一列:

      df.columns = df.columns[:1].tolist() + df.columns[1:].astype(int).tolist()
      
      arr = justify(df.to_numpy()[:, 1:], invalid_val=np.nan)
      df1 = pd.DataFrame(arr, index=df.index, columns=df.columns[1:] + 1)
      df1.insert(0,'ID', df['ID'])
      print (df1)
             ID       1       2       3       4       5       6       7       8  \
      300  1001  1001.0  1002.0  1001.0  1002.0     NaN     NaN     NaN     NaN   
      301  1010  1010.0  1000.0  2000.0  1234.0  1213.0  1415.0     NaN     NaN   
      302  1100  1234.0  5678.0  9101.0  1121.0  3141.0  2345.0  6789.0  1011.0   
      303  1000  2001.0  9876.0  1001.0  1002.0     NaN     NaN     NaN     NaN   
      
                9      10  
      300     NaN     NaN  
      301     NaN     NaN  
      302  1617.0  1819.0  
      303     NaN     NaN  
      

      【讨论】:

        猜你喜欢
        • 1970-01-01
        • 1970-01-01
        • 2023-01-28
        • 2017-10-16
        • 2020-11-23
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 2021-12-04
        相关资源
        最近更新 更多