为了账号安全,请及时绑定邮箱和手机立即绑定

如何将最近的线关联到 Python 中的每个给定点?

如何将最近的线关联到 Python 中的每个给定点?

千巷猫影 2023-04-11 15:48:42
我有两个 Pandas DataFrame,第一个名为Points,列为“ longitude ”和“ latitude ”(即地理坐标);并且,第二个数据框被命名为具有以下列的链接:第一个点为“ lon1 ”和“ lat1 ”,第二个点为“ lon2 ”和“ lat2 ”然后每行中给出的每对点创建一个链接/线. 此外,对于Links DataFrame,它有一个名为“ link_id ”的列。比如说,大约有 10 个点和 4,000 个链接。我如何通过返回'link_id'并将其作为名为' closest_link '的附加列附加到Points DataFrame来将每个给定点关联到最近的链接/线?
查看完整描述

1 回答

?
森栏

TA贡献1810条经验 获得超5个赞

这是一种可能有效的方法。考虑:

  1. 在两个数据框PointsLinks之间生成叉积,

  2. 然后对新 DataFrame 中的每一应用一个函数。

  3. 查找函数为每个组报告的最小距离。

我们将新的 df 称为PointsLinks

下面是一些采用这种方法的代码:

import pandas as pd

import random        


Points = pd.DataFrame( [ [ 1,2 ], [ 3,4 ], [ 5,6 ] ], columns = [ 'longitude', 'latitude' ] )

Links = pd.DataFrame( [ [ 'Link1', ( 4,3 ) , ( -1, -2 ) ], [ 'Link2', (10,10) , ( -5, -5 ) ] ], columns = [ 'linkid', 'lon1&lat1', 'lon2&lat2' ] )


   

print(Points) 

print(Links)         


#Step 1:  https://stackoverflow.com/questions/53699012/performant-cartesian-product-cross-join-with-pandas

def cartesian_product_basic(left, right):

    return (         

       left.assign(key=1).merge(right.assign(key=1), on='key').drop('key', 1))

   

def DistanceToLink( pointlink ): 

  return random.randrange(10)  


PointsLinks = cartesian_product_basic(Points,Links)       

print( PointsLinks ) 


#Step 2: https://stackoverflow.com/questions/26886653/pandas-create-new-column-based-on-values-from-other-columns-apply-a-function-o

PointsLinks['distance'] = PointsLinks.apply( lambda row : DistanceToLink(row), axis = 'columns' )



print( PointsLinks )


#Step 3:  Find the smallest distance per group https://stackoverflow.com/questions/27842613/pandas-groupby-sort-within-groups

closest = PointsLinks.sort_values( [ 'latitude', 'longitude', 'distance' ] , ascending = True ).groupby(  [ 'latitude', 'longitude'] ).head(1)


# Drop the unnecessary columns

closest.drop( columns = ['lon1&lat1','lon2&lat2','distance'] , inplace=True) 

print(closest)

以下是代码创建的数据框:


要点:


   longitude  latitude

0          1         2

1          3         4

2          5         6 

链接:


  linkid lon1&lat1 lon2&lat2

0  Link1    (4, 3)  (-1, -2)

1  Link2  (10, 10)  (-5, -5)

然后是 PointsLinks(在使用 apply() 添加距离列之后:


   longitude  latitude linkid lon1&lat1 lon2&lat2  distance

0          1         2  Link1    (4, 3)  (-1, -2)         1

1          1         2  Link2  (10, 10)  (-5, -5)         6

2          3         4  Link1    (4, 3)  (-1, -2)         0

3          3         4  Link2  (10, 10)  (-5, -5)         9

4          5         6  Link1    (4, 3)  (-1, -2)         5

5          5         6  Link2  (10, 10)  (-5, -5)         1

我没有实施DistanceToLink。我只是在那里放了一个随机数生成器。这是第一个pointlink对象的样子(它是一个代表一行的系列):


longitude           1

latitude            2

linkid          Link1

lon1&lat1      (4, 3)

lon2&lat2    (-1, -2)

现在您有了每个组合的距离,您可以找到并选择具有最短距离的 PointLink 对(使用pandas groupby sort within groups):


closest = PointsLinks.sort_values( [ 'latitude', 'longitude', 'distance' ] , ascending = True ).groupby(  [ 'latitude', 'longitude'] ).head(1)

以下是结果:


   longitude  latitude linkid

0          1         2  Link1

2          3         4  Link1

5          5         6  Link2


查看完整回答
反对 回复 2023-04-11
  • 1 回答
  • 0 关注
  • 100 浏览
慕课专栏
更多

添加回答

举报

0/150
提交
取消
意见反馈 帮助中心 APP下载
官方微信