【发布时间】:2021-07-11 23:06:29
【问题描述】:
我有两张桌子 - 经销商和客户。对于客户表中的每个客户位置,我需要从经销商表中找到最近的经销商。
我有一个可以运行但需要几个小时才能运行的代码。我需要帮助来优化我的解决方案。
dealer 表有 25k+ 行,customer 表有 200k+ 行。两个表都有 3 个主要列:(DealerID、Lat、Long)和(CustomerID、Lat、Long)。我的输出看起来像这样:
| CustomerID | Lat | Long | ClosestDealer | Distance |
|---|---|---|---|---|
| Customer1 | 61.61 | -149.58 | Dealer3 | 15.53 |
| Customer2 | 42.37 | -72.52 | Dealer258 | 8.02 |
| Customer3 | 42.42 | -72.1 | Dealer1076 | 32.92 |
| Customer4 | 31.59 | -89.87 | Dealer32 | 3.85 |
| Customer5 | 36.75 | -94.84 | Dealer726 | 7.90 |
我当前的解决方案:遍历所有数据行以找到最小值。距离会太长。为了优化这一点,我根据经纬度点的向下舍入版本对两个表中的数据进行了分组,然后将它们加在一起以得出我的最终组(请参阅下面的“LatLongGroup”列)。
| CustomerID | Lat | Long | LatGroup | LongGroup | LatLongGroup |
|---|---|---|---|---|---|
| Customer1 | 61.61 | -149.58 | 61 | -149 | -88 |
| Customer2 | 42.37 | -72.52 | 42 | -72 | -30 |
| Customer3 | 42.42 | -72.1 | 42 | -72 | -30 |
| Customer4 | 31.59 | -89.87 | 31 | -89 | -58 |
| Customer5 | 36.75 | -94.84 | 36 | -94 | -58 |
这两个表都根据“LatLongGroup”列进行排序。我有一个名为 group 的单独表,它为经销商表提供每个组的起始行号和结束行号。 然后,我匹配经销商表中与 customerID 具有相同“Latlonggroup”的记录。这有助于我缩小对最近经销商的搜索范围。
但有时最近的经销商可能不在同一组中,因此为避免任何陷阱,我不仅搜索匹配的组,还搜索上下一个。 View Currently Used Code
请让我知道优化此问题的最佳方法是什么,或者是否有更简单的方法可以为此类大型数据集找到最近的经销商。非常感谢任何方向。谢谢!
col_names = ["CustomerKey","DealerKey","Dist"]
df = pd.DataFrame(columns = col_names)
c = 0
for i in range(0,len(df_c)):
print(i)
row = {'CustomerKey':df_c.loc[i,'ZIPBRANDKEY'],'DealerKey':'','Dist':0}
df = df.append(row, ignore_index=True)
a = group[group['LatLongGroup'] == df_c.LatLongGroup[i]].index[0]
if(a-1 >= 0):
start = group.loc[a-1,'Start']
else:
start = group.loc[a,'Start']
if(a+1 < len(group)):
end = group.loc[a+1,'End']
else:
end = group.loc[a,'End']
t1 = 0
for j in range(start,end):
dist = round(geopy.distance.distance(df_c.Lat_long[i], df_s.Lat_long[j]).miles,2)
if(t1 == 0):
min_dist = dist
dealerkey = df_s.loc[j,'DEALER_BRAND_KEY']
t1 = 1
elif(dist < min_dist):
min_dist = dist
dealerkey = df_s.loc[j,'DEALER_BRAND_KEY']
df.loc[c,'DealerKey'] = dealerkey
df.loc[c,'Dist'] = min_dist
c = c+1
df.head()
作为参考,上面提到的组数据框如下所示:
| Group | Start | End |
|---|---|---|
| -138 | 0 | 7 |
| -137 | 7 | 15 |
| -136 | 15 | 53 |
| -135 | 53 | 55 |
| -88 | 55 | 78 |
【问题讨论】:
-
您可以使用 tthis approach 查找数据集中每个点与第二个数据集的最近邻。在这里,提问者的数据集中有数百万个点。
-
嘿,谢谢你把我指向那个帖子。我目前使用了 KDTree 方法并且它有效。我还将研究 Ballree 方法。
标签: python python-3.x pandas optimization geopy