如何跨多个数据集管理查找

时间:2017-12-01 17:01:04

标签: python excel pandas time-complexity

我刚开始使用大数据,并尝试将一些CSV查找复制到Pandas代码中。在较小的数据集上,我已经能够使用嵌套循环。

CSV中的查找是这样的,它们遍历datasheet1中的所有行,匹配datasheet2中的两个字段,如果匹配则设置数据表1的行值:

=IFERROR(
    IF(
        ISBLANK(
            INDEX(RefTable!$D:$D,MATCH($E6,RefTable!$A:$A,0))
        ),
        "",                                                                                 
        INDEX(RefTable!$D:$D,MATCH($E6,RefTable!$A:$A,0))
    ),
    ""
)

当我尝试在Pandas中执行此操作时,它最终会成为O(n^2)操作,这会变得非常慢。例如,查找特定行的匹配城市然后设置状态:

# total loops: 1000x100 = 100,000
for i, row in dataframe1.iterrows(): # 1000 rows
    for j, row2 in dataframe2.iterrows(): # 100 rows
       if row['market_city'] == row2['city']:
                dataframe1.loc[i, 'state'] = row2['state']

如何将其分解为更易于管理的内容,例如O(n)

2 个答案:

答案 0 :(得分:0)

您应该可以使用merge。不要在这台机器上安装python进行测试,但是类似于:

df3 = dataframe1.merge(dataframe2, 
                       left_on = 'market_city', 
                       right_on = 'city', 
                       how='left').drop(['state_x', 'city'], axis=1)

上面的代码将创建一个与dataframe1相同的新数据框,但是当market_city与city匹配时,将使用dataframe2中的状态。如果这仍然不够快,join()可能会更快。

值得注意的是,加入索引的速度更快,因此您可以按如下方式设置索引:

dataframe1.set_index('market_city', inplace=True)
dataframe2.set_index('city', inplace=True)

答案 1 :(得分:0)

哇,这个问题非常有趣,有时优化代码也很有趣。

我尝试了几行而不使用for循环给了我结果。

我已经创建了两个数据集,如问题中所述

df1 = pd.DataFrame({"market_city":["AM","CM","BM","EM","DM"],
                    "state":["ROM","AOM","SOM","DOM","VOM"]})
print(df1)
  market_city state
0          AM   ROM
1          CM   AOM
2          BM   SOM
3          EM   DOM
4          DM   VOM

df2 = pd.DataFrame({"city":["CM","KM","AM"],"state":["ZOM","TOM","KOM"]})
print(df2)
  city state
0   CM   ZOM
1   KM   TOM
2   AM   KOM

现在,由于我们有两个数据框,我们在df1状态替换df2状态,我们看到df1的market_city与df2城市之间的匹配

<强>代码

dct_val = dict(zip(df2['city'], df2.state))
df1['state'] = df1['market_city'].replace(dct_val)

print(df1)
  market_city state
0          AM   KOM
1          CM   ZOM
2          BM    BM
3          EM    EM
4          DM    DM