匹配2个数据帧的熊猫列值

时间:2018-10-30 15:26:18

标签: python pandas

设置

我有2个熊猫数据框:

  1. df_ads:每一行包含一个拆下的房屋广告的信息,df_ads['ad_post_code']包含广告的荷兰邮政编码。
  2. df_mapping:邮政编码与NUTS3地区之间的映射

我需要将每个广告的邮政编码映射到其NUTS3区域。


数据框

df_ads['ad_post_code']看起来像

0                1567 JA
1                3893 GB
2                5091 BE
3                1087 MB
4                7905 GW
5                5121 ZH

其中len(df_ads['ad_post_code']) = 85447

df_mapping外观

      CODE NUTS_3
0     1011  NL326
1     1012  NL326
2     1013  NL326
3     1014  NL326
4     1015  NL326
5     1016  NL326

其中len(df_mapping) = 4074df_mapping['CODE']显示荷兰邮政编码的前4个字符,而df_mapping['NUTS_3']是邮政编码的NUTS3区域。

换句话说,邮政编码1011位于NUTS3区域NL326中。


问题

我已经做了一些简单的循环,将df_ads中的广告映射到NUTS3区域。但是,我似乎无法编写正确的循环设置。

nuts3_map = []

# insert postal codes into list
for i in range(0,len(df_ads)):

    postal_code_ad = df_ads['ad_post_code'].iloc[i].split()[0]

    for j in range(0,len(df_mapping)):

        postal_code_map = str(df_mapping['CODE'].iloc[j])

        # check if postal code match
        if postal_code_ad == postal_code_map:

            nuts3_map.append(df_mapping['NUTS_3'].iloc[j])

            break
    continue

运行此命令会得到len(nuts3_map) = 85353,而len(df_ads) = 85448,这样df_ads['nuts3'] = nuts3就会得到ValueError: Length of values does not match length of index

double for循环是最快的方法吗?如果是这样,如何解决我的for循环,使其一切正常?

1 个答案:

答案 0 :(得分:0)

我首先要在df_ads中创建另一列:

# If `df_mapping['CODE']` is `int`
df_ads['CODE'] = df_ads['ad_post_code'].apply(lambda x: int(x[:4]))

# If `df_mapping['CODE']` is `str`
# df_ads['CODE'] = df_ads['ad_post_code'].apply(lambda x: x[:4])

然后,我将使用DataFrame.merge对两个数据帧进行内部合并:

df_ads.merge(df_mapping, left_on='CODE', right_on='CODE', how='inner')

我可以自由地修改您的数据以产生可行的示例:

# df_ads['ad_post_code']
0    1567 JA
1    3893 GB
2    5091 BE
3    1087 MB
4    7905 GW
5    5121 ZH
6    1011 XX

# df_mapping
   CODE NUTS_3
0  1011  NL326
1  1012  NL326
2  1013  NL326
3  1014  NL326
4  1015  NL326
5  1016  NL326
6  1567  XSFDF

输出:

  ad_post_code  CODE NUTS_3
0      1567 JA  1567  XSFDF
1      1011 XX  1011  NL326

如果df_ads['CODE']中的每个代码都在df_mapping['CODE']中存在,那么您应该获得正确的输出。

编辑

如果您想知道df_mapping中的列表是否完整,可以执行以下操作:

df_ads.loc [np.logical_not(df_ads ['CODE']。isin(df_mapping ['CODE']))]

缺少数据:

   ad_post_code  CODE
id                   
1       3893 GB  3893
2       5091 BE  5091
3       1087 MB  1087
4       7905 GW  7905
5       5121 ZH  5121