代码之家  ›  专栏  ›  技术社区  ›  Dan Grossnickle

Pandas交叉表矩阵点nansum

  •  2
  • Dan Grossnickle  · 技术社区  · 7 年前

    我正在寻找使用np从现有数据帧创建子数据帧的帮助。类nansum函数。我想将此表转换为非空列和的矩阵:

        dan ste bob
    t1  na  2   na
    t2  2   na  1
    t3  2   1   na
    t4  1   na  2
    t5  na  1   2
    t6  2   1   na
    t7  1   na  2
    

    例如,当“dan”不为null(t-2,3,4,6,7)“ste”的和为2,“bob”的和为5。当“ste”不为空时,“dan”的和为4。

        dan ste bob
    dan 0   2   5
    ste 4   0   2
    bob 4   1   0
    

    有什么想法吗?

    提前感谢!

    我最终使用了matt函数的修改版本,如下所示:

    def nansum_matrix_create(df):
        rows = []
        for col in list(df.columns.values):
    
            col_sums = df[df[col] != 0].sum()
            rows.append(col_sums)
    
        return pd.DataFrame(rows, columns=df.columns, index=df.columns)
    
    2 回复  |  直到 6 年前
        1
  •  2
  •   piRSquared    7 年前
    1. 使用 pd.DataFrame.notnull 获取非空值的位置。
    2. 然后使用 pd.DataFrame.dot
    3. 最后,使用 np.eye 将对角线归零。

    df.notnull().T.dot(df.fillna(0)) * (1 - np.eye(df.shape[1]))
    
         dan  ste  bob
    dan  0.0  2.0  5.0
    ste  4.0  0.0  2.0
    bob  4.0  1.0  0.0
    

    注:
    我用它来确保我的值是数字。

    df = df.apply(pd.to_numeric, errors='coerce')
    
        2
  •  0
  •   Matt    7 年前

    假设您的数据帧没有大量的列,这个函数应该做您想要做的事情,并且性能相当好。我已经使用 for 在列之间循环,这样可能会有一个更高性能/优雅的解决方案。

    import pandas as pd
    
    # Initialise dataframe
    df = {"dan":[pd.np.nan,2,2,1,pd.np.nan,2,1],
          "ste":[2,pd.np.nan,1,pd.np.nan,1,1,pd.np.nan],
          "bob":[pd.np.nan,1,pd.np.nan,2,2,pd.np.nan,2]}
    df = pd.DataFrame(df)[["dan","ste","bob"]]
    
    def matrix_create(df):
        rows = []
        for col in df.columns:
            subvals, index = [], []
            for subcol in df.columns:
                index.append(subcol)
                if subcol == col:
                    subvals.append(0)
                else:
                    subvals.append(df[~pd.isnull(df[col])][subcol].sum())
    
            rows.append(subvals)
    
        return pd.DataFrame(rows,columns=df.columns,index=index)
    
    matrix_create(df)