Warm tip: This article is reproduced from serverfault.com, please click

python-在两个DataFrame之间执行大量Pandas查找的最佳方法

(python - Best way to perform multiple amount of Pandas lookups between two DataFrames)

发布于 2020-11-27 23:56:10

我正在尝试使用两个数据框来使用Pandas进行简单查找。我有一个主要的主数据框(左)和一个查找数据框(右)。我想在匹配的整数代码上加入它们,并title从中返回该项目item_df

我看到一个关于键值对的想法的解决方案,但似乎很麻烦。我的想法是merge使用col3name作为键列将数据帧放在一起并保持value正确的帧(我想要的是)title因此,我决定参加dropkey专栏文章只剩下value现在,让我说说我想使用自己的手动命名约定来多次执行此操作。为此,我使用rename重命名合并后的值。现在,我将重复此合并操作,并将下一个联接重命名为类似second_title(请参见下面的示例)。

是否有一种不那么麻烦的方法来执行此重复操作,而无需不断删除合并的多余列并在每个合并步骤之间重命名新列?

下面的示例代码:

import pandas as pd

master_dict: dict = {'col1': [3,4,8,10], 'col2': [5,6,9,10], 'col3': [50,55,59,60]}
master_df: pd.DataFrame = pd.DataFrame(master_dict)
item_dict: dict = {'name': [55,59,50,5,6,7], 'title': ['p1','p2','p3','p4','p5','p6']}
item_df: pd.DataFrame = pd.DataFrame(item_dict)
    
print(master_df.head())
   col1  col2  col3
0     3     5    50
1     4     6    55
2     8     9    59
3    10    10    60
print(item_df.head())
   name title
0    55    p1
1    59    p2
2    50    p3
3     5    p4
4     6    p5

# merge on col3 and name
combined_df = pd.merge(master_df, item_df, how = 'left', left_on = 'col3', right_on = 'name')
# rename title to "first_title"
combined_df.rename(columns = {'title':'first_title'}, inplace = True)
combined_df.drop(columns = ['name'], inplace = True) # remove 'name' column that was joined in from right frame
# repeat operation for "second_title"
combined_df = pd.merge(combined_df, item_df, how = 'left', left_on = 'col2', right_on = 'name')
combined_df.rename(columns = {'title': 'second_title'}, inplace = True)
combined_df.drop(columns = ['name'], inplace = True)
print(combined_df.head())
   col1  col2  col3 first_title second_title
0     3     5    50          p3           p4
1     4     6    55          p1           p5
2     8     9    59          p2          NaN
3    10    10    60         NaN          NaN
Questioner
Coldchain9
Viewed
33
sammywemmy 2020-11-29 08:47:00

我们可以将你的key:value映射与map函数一起使用:

下面的代码获取分别namemaster_dfcol3和col2中的item_df的值的字典

col3 = dict(zip(*(value for _, value in
                  item_df[item_df.name.isin(master_df.col3)].items()))
           )

col2 = dict(zip(*(value for _, value in
                 item_df[item_df.name.isin(master_df.col2)].items()))
           )


col3
{55: 'p1', 59: 'p2', 50: 'p3'}

col2
{5: 'p4', 6: 'p5'}

接下来是使用分配并创建列first_title和second_title:

master_df.assign(
    first_title=master_df.col3.map(col3),
    second_title=master_df.col2.map(col2)
    )



   col1 col2    col3    first_title second_title
0   3   5       50      p3            p4
1   4   6       55      p1            p5
2   8   9       59      p2            NaN
3   10  10      60      NaN           NaN

更新

我考虑过你对一本字典的评论,并且似乎可以通过使用“系列”来实现。这将大大减少我之前共享的code肿代码。在这种情况下,我们将转换item_df为序列并将其映射到每个相关列:

item_df = item_df.set_index("name").loc[:, "title"]

item_df

name
55    p1
59    p2
50    p3
5     p4
6     p5
7     p6
Name: title, dtype: object

现在使用assign函数创建你的特定列:

master_df.assign(first_title=master_df.col3.map(item_df), 
                 second_title=master_df.col2.map(item_df)
                 )

   col1 col2    col3    first_title second_title
0   3   5       50      p3            p4
1   4   6       55      p1            p5
2   8   9       59      p2            NaN
3   10  10      60      NaN           NaN

更简单直接。