2017-08-10 112 views
4

序幕:如何GeoDjango內置兩個點之間計算3D距離(包括高度)

這是SO經常產生的問題:

我想編寫SO文檔的示例,但geodjango章節從未起飛,並且自從文檔在2017年8月8日關閉後,我將按照this widely upvoted and discussed meta answer的建議編寫我的示例作爲自我回復的帖子。

當然,我很樂意看到任何不同的方法!


問:

假設模型:

class MyModel(models.Model): 
    name = models.CharField() 
    coordinates = models.PointField() 

我在哪裏存儲在coordinate變量點作爲lan, lng, alt點:

MyModel.objects.create(
    name='point_name', 
    coordinates='SRID=3857;POINT Z (100.00 10.00 150)') 

我想計算三維距離即可補間兩個這樣的點:

p1 = MyModel.objects.get(name='point_1').coordinates 
p2 = MyModel.objects.get(name='point_2').coordinates 

d = Distance(m=p1.distance(p2)) 

現在d=X米。

如果我僅改變有問題的點中的一個的高度:

例如:

p1.coordinates = 'SRID=3857;POINT Z (100.00 10.00 200)' 

從150先前,計算:

d = Distance(m=p1.distance(p2)) 

返回d=X再次,像海拔被忽略。
如何計算我的積分之間的3D距離?

回答

3

GeoDjango Distance計算兩點之間的二維距離,並沒有考慮到高度差異。
爲了獲得3D計算,我們需要創建一個距離函數,將考慮在計算海拔差異:

理論:

latitudelongitudealtitudePolar coordinates,我們需要將它們翻譯爲Cartesian coordinates (x, y, z)以便將Euclidean Formula應用於它們並計算它們的3D距離。

  • 假設:
    polar_point_1 = (long_1, lat_1, alt_1)

    polar_point_2 = (long_2, lat_2, alt_2)

  • 翻譯每個點是笛卡爾相當於利用這個公式:

    x = alt * cos(lat) * sin(long) 
    y = alt * sin(lat) 
    z = alt * cos(lat) * cos(long) 
    

    ,你將分別有p_1 = (x_1, y_1, z_1)p_2 = (x_2, y_2, z_2)點。

  • 最後用歐幾里德公式:

    dist = sqrt((x_2-x_1)**2 + (y_2-y_1)**2 + (z_2-z_1)**2) 
    
1

一旦轉換成直角座標系,可以計算與numpy的規範:

np.linalg.norm(point_1 - point_2) 
相關問題