【问题标题】:Remove rows from dataframes not present in dataframes in dictionary从字典中的数据框中不存在的数据框中删除行
【发布时间】:2022-01-15 23:59:20
【问题描述】:

我有数百个 pandas 数据框,例如:

Df1 = 
    MD    A    B    C  
    r1    6    3    9   
    r2    2    1    1  
    r3    5    7    2  
    r4    8    2    0

Df2 = 
    MD    A    B    C  
    r1    1    7    1  
    r2    6    3    0  
    r3    3    1    8
    r4    1    7    4

我也有一本这样的字典(除了有许多键和值来反映数据帧的数量):

Dict = {'D1', MD
              r1
              r4
        [2 rows x 1 columns]
        'D2', MD
              r1
              r2
              r3
        [3 rows x 1 columns]}
  

我需要的是一种遍历字典的方法,对于每个数据帧和相应的键(即 Df1 和 D1,以及 Df2 和 D2),删除“字典值数据帧”中不存在的行。

所以对于 Df1,我需要转到键 D1 并删除不在该键的数据框中的行。即从 Df1 中删除 r2 和 r3。

所以我想要的结果是:

Df1 = 
    MD    A    B    C  
    r1    6    3    9   
    r4    8    2    0

Df2 = 
    MD    A    B    C  
    r1    1    7    1  
    r2    6    3    0  
    r3    3    1    8

非常感谢任何帮助!

PS。如果保留行而不是删除行更容易,那也会很有帮助!

【问题讨论】:

    标签: python pandas dataframe dictionary


    【解决方案1】:

    这里我只是打印值,但您可以重新分配 DataFrame。

    >>> df1 = pd.DataFrame.from_dict({"r1": [1,2,3], "r2": [4,5,6], "r3": [7,8,9]}, columns=["A", "B", "C"], orient="index")
    >>> df2 = pd.DataFrame.from_dict({"r1": [1,2,3], "r2": [4,5,6], "r3": [7,8,9]}, columns=["A", "B", "C"], orient="index")
    
    >>> dfs = [df1, df2]
    >>> dfs
    
    [    A  B  C
     r1  1  2  3
     r2  4  5  6
     r3  7  8  9,
         A  B  C
     r1  1  2  3
     r2  4  5  6
     r3  7  8  9]
    
    lookup = {"d1": ["r1", 'r2'], 'd2': ["r2", "r3"]}
    
    for rows, df in zip(lookup.values(), dfs):
        print(df.loc[rows])
    
        A  B  C
    r1  1  2  3
    r2  4  5  6
        A  B  C
    r2  4  5  6
    r3  7  8  9
    

    编辑

    如果您的 DataFrames 不在 dict 中并且仅可用作全局变量,提供键匹配在您查找变量名称时,您可以执行以下操作:

    >>> df1 = pd.DataFrame.from_dict({"r1": [1,2,3], "r2": [4,5,6], "r3": [7,8,9]}, columns=["A", "B", "C"], orient="index")
    >>> df2 = pd.DataFrame.from_dict({"r1": [1,2,3], "r2": [4,5,6], "r3": [7,8,9]}, columns=["A", "B", "C"], orient="index")
    
    >>> lookup = {"df1": ["r1", 'r2'], 'df2': ["r2", "r3"]}
    
    # Use the reference key from lookup, to grab the relevant DataFrame
    # then index rows using .loc with the corresponding values from lookup
    for key in lookup.keys():
        print(globals()[key].loc[lookup[key]])
    

    否则,我建议将它们放入可以轻松迭代的数据结构中,如原始答案所示。

    【讨论】:

    • 我拥有的数据框不在字典中。它们是独立的。有什么方法可以在多个单独的数据帧上执行此操作,还是我应该先从所有数据帧中制作一个字典?
    • @FrustratedApe 我已经用一个我认为你的意思的例子更新了我的答案。我认为如果您将 DataFrames 放在可以迭代的数据结构中会更容易,因为您不必担心键匹配,只要所有内容都按相同的顺序排列。然而,我已经包含了一个处理仅在全局上下文中的 DataFrame 的示例。
    • 我尝试按照您在编辑中建议的方式进行操作,但最终出现以下错误:ValueError: Cannot index with multidimensional key。如果我只是尝试打印 key 或 globals()[key] 我会得到预期的结果。即:for key in lookup.keys(): print(globals()[key]) for key in lookup.keys(): print(globals()[key])
    • 这行得通,但我必须先将数据框转换为列表。
    【解决方案2】:

    你的字典有点怪,所以我把它编辑成下面的dct。基本上每个键都有一个对应的数据框。然后您可以zipdct.values() 使用字典列表并索引您的相关数据框。

    dct = {'D1': {'MD': ['r1', 'r4']},
           'D2': {'MD': ['r1', 'r2', 'r3']}
          }
    df1_new, df2_new = [df[df['MD'].isin(v['MD'])] for v, df in zip(dct.values(),[df1,df2])]
    

    输出:

       MD  A  B  C
     0  r1  6  3  9
     3  r4  8  2  0
    
        MD  A  B  C
     0  r1  1  7  1
     1  r2  6  3  0
     2  r3  3  1  8
    

    【讨论】:

    • 遗憾的是,我拥有的字典是我从我使用的设备中得出的标准。我在那本字典里有一百多个键,所以编辑它会很费时间。我也有数百个数据框,所以像这样做 zip 会很耗时。抱歉,如果我在问题中不清楚这一点。我将对其进行编辑以反映这一点。
    猜你喜欢
    • 1970-01-01
    • 2020-03-18
    • 1970-01-01
    • 2016-11-12
    • 2021-10-31
    • 2016-01-07
    • 1970-01-01
    • 1970-01-01
    • 2016-11-13
    相关资源
    最近更新 更多