Jag har provat flera sätt att mäta avståndet mellan två punkter i min Django-applikation och jämföra resultaten med en tillförlitlig mätning. siffrorna är långt av. Jag antar till exempel att det verkliga avståndet mellan Dublin och Liverpool är ~ 217 km som rapporterats av Google Maps:

ange bildbeskrivning här

Använda geopy (ska vara extremt exakt ):

>>> from geopy.distance import distance >>> dublin = (-6.270447, 53.339791) >>> liverpool = (-2.991028, 53.402061) >>> distance(dublin, liverpool).km 362.70989455939394 

Med hjälp av Django ”s GEOS API (mindre exakt linjär beräkning):

>>> from django.contrib.gis.geos import Point >>> dublin = Point(-6.270447, 53.339791, srid=3857) >>> liverpool = Point(-2.991028, 53.402061, srid=3857) >>> dublin.distance(liverpool)*100 328.00101418228877 

EDIT: Använd en bättre projektion för detta område (UTM 30N) ger nästan samma resultat:

>>> dublin.transform(32630) >>> liverpool.transform(32630) >>> dublin.distance(liverpool)*100 328.32200116442266 

I båda fallen är jag av över 100 km! Mätning av små avstånd (< 1 km) är lika felaktig. Vad gör jag fel här !?

Kommentarer

  • För ditt django-exempel, inte ' t EPSG: 3857 använder mätare istället för grader ?
  • Mercator ska aldrig användas för avståndsmätning, särskilt inte så långt norrut.
  • Jag försökte förvandla punkterna till 32630 (UTM-zon 30N) och fick 328,3 km. Nästan ingen skillnad i det här fallet. Det finns ' ingenting om projektion i geopy docs eller i andra svar, och Vincenty-avståndet jag får ska vara exakt på mm-nivån .
  • dublin.distance(liverpool)*100 < – Det faktum att du var tvungen att multiplicera med 100 istället för 1000 borde berätta något misstänksam pågår här.

Svar

Om du inverterar koordinaterna fungerar det inte (geopy använder (latitud, longitud) i WGS84 crs)

 dublin = (53.33306,-6.24889) liverpool = ( 53.41058,-2.97794) print distance(dublin, liverpool).km 217.863019038 print(vincenty(dublin, liverpool).kilometers) 217.863019038 print(great_circle(dublin, liverpool).kilometers) 217.211596704 

GEOS ( välformad , django ) använder ett kartesiskt plan och det euklidiska avståndet. Med pyproj (django använder (longitud, latitud))

from django.contrib.gis.geos import Point dublin = Point(-6.270447, 53.339791, srid=4326) # in degrees liverpool = Point(-2.991028, 53.402061, srid=4326) # in degrees dublin.distance(liverpool)*100 328.00101418228877 # units ? import pyproj # conversion from WGS84 to epsg:3857 p1 = pyproj.Proj(proj="latlong",datum="WGS84") p2 = pyproj.Proj(init="epsg:3857") a = pyproj.transform(p1,p2,-6.270447, 53.339791) b = pyproj.transform(p1,p2,-2.991028, 53.402061) dublin = Point(a) # in meters liverpool = Point(b) # in meters dublin.distance(liverpool)/1000 # Euclidean 365.2480859440489 #in km 

Men, som Vince säger att Mercator-projektionen aldrig ska användas för avståndsmätning.

Med EPSG: 32630 (UTM-zon 30N):

p3 = pyproj.Proj(init="epsg:32630") a = pyproj.transform(p1,p3,-6.270447, 53.339791) b = pyproj.transform(p1,p3,-2.991028, 53.402061) dublin = Point(a) liverpool = Point(b) dublin.distance(liverpool)/1000 218.32514783088294 #in km 

Och alla resultat (geopy och django) är jämförbara med Googles avstånd eller Avstånd från Liverpool till Dublin (218 km)

Kommentarer

  • Lon, lat / lat, lon förvirring slår igen! Jag var säker på att jag hade det precis där.

Lämna ett svar

Din e-postadress kommer inte publiceras. Obligatoriska fält är märkta *