簡體   English   中英

優化 2 個 **long** 二維點陣列之間的距離計算

[英]Optimize distance calculations between 2 **long**, 2-D arrays of points

我試圖通過使用“應用”函數在數據幀的所有行上應用內聯函數來避免循環。

問題是,我有大約 800 個點(卡車停靠點),我試圖確定其中哪些是沿着某條路線的,該路線本身由大約 100k 點定義。

我的方法是計算卡車停靠站到路線上每個點之間的歐幾里德距離,如果這些距離中的任何一個小於某個值,我就會保留路線。

我最初是通過循環來做到這一點的,但它非常慢(假設我在距離小於某個值時不會中斷循環,就像 100k*800 次迭代)。

所以我嘗試使用“應用”,但它仍然很慢。 有誰知道我可以優化這個的方法嗎?

完整代碼:

import pandas as pd
import numpy as np
import time, os

BASE_DIR='C:\\Users\\aidenm\\Desktop\\geo'

rt_df = pd.read_csv(os.path.join(BASE_DIR, 'test_route.txt'))
'''
lon, lat
-118.410339, 34.019653
-118.410805, 34.020241
-118.411301, 34.020863
-118.411766, 34.021458
...
'''

fm_df = pd.read_csv(os.path.join(BASE_DIR, 'test_fm.txt'))
'''
lat, lon
41.033959, -77.515672
41.785524, -80.853175
41.128748, -80.769934
41.465085, -82.060677
...
'''



def is_on_route_inline(x, route_coordinates):
    '''

    :param route_coordinates:
    :param fencing_module_coordinate:
    :return: True if on route else False
    '''



    a = np.array((float(x[0]), float(x[1])))
    # bs = [np.array((c[1], c[0])) for c in rcs]


    def distance_inline(b, fcm_point):
        return np.linalg.norm(b-fcm_point)

    # bss = pd.Series(bs)
    distances = route_coordinates.apply(distance_inline, args=(a,), axis=1)   #np.linalg.norm(a-b))

    # distances = [np.linalg.norm(a-b) for b in bs]

    if min(distances)<0.1:
        print(x)
        return True

    return False

fm_df.apply(is_on_route_inline,  args=(rt_df,), axis=1)#rt_df)



要快速執行此操作,您需要將 DataFrame 中的數據轉換為 Numpy 數組。 首先,讓我們計算一個卡車停靠點和所有路線點之間的距離——

# Create Numpy array of shape (100k, 2)
route_points = rt_df[['lat', 'lon']].values

truck_stop = # get one truck stop location shape (2, )

# Compute distances
dists = np.linalg.norm(route_points - truck_stop, axis=1) 

這讓 Numpy 廣播為您處理所有路由位置的循環(非常快)。 但是,聽起來您真正需要的是所有卡車停靠點和路線點之間的距離。 讓 Numpy 廣播來做到這一點很棘手,所以我建議使用scipy.spatial.distance_matrix

from scipy.spatial import distance_matrix

route_points = rt_df[['lat', 'lon']].values  # shape (100k, 2)
truck_points = fm_df[['lat', 'lon']].values  # shape (800, 2)

all_distances = distance_matrix(route_points, truck_points) # shape (100k, 800)

現在all_distances是一個包含所有成對距離的 Numpy 數組,所以all_distances[i, j]是路線i和卡車停靠點j之間的距離。 同樣,這讓 Numpy 可以為您處理 100k * 800 次迭代,並且速度非常快。 (在我的筆記本電腦上,用類似大小的陣列完成這個需要大約 3 秒)。

之后,你可以找到足夠小的距離

all_distances < 0.1

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM