我正在构建一张世界地图,希望用户能够查找位置并按照世界任何地方的距离对其进行排序。我使用GeoDjango计算距离,然而,返回的距离似乎是错误的,所以我根据geopy
的计算检查它们。
距离差别很大,如果结果按公里的DB距离值与公里的geopy
值进行排序,则它们的顺序不一样。
我假设geopy
值是正确的,所以我想知道,我实施GeoDjango的方式有问题吗?
它是否正常工作?
这是否与尝试计算整个世界的距离有关,而不仅仅是一个可能有srid
的特定区域?
views.py
pnt = GEOSGeometry('POINT({} {})'.format(latitude, longitude), srid=4326)
qs = Place.filter(point__distance_lte=(pnt, D(km=radius*2))).annotate(distance=Distance('point', pnt)).order_by('distance')
settings.py
DATABASES = {
'default': {
'ENGINE': 'django.contrib.gis.db.backends.postgis',
'USER': '',
'NAME': 'places',
'HOST': '127.0.0.1',
'PORT': '5432',
}
}
models.py
:
from django.contrib.gis.db import models
from geopy.distance import vincenty
class Place(models.Model):
latitude = models.DecimalField(max_digits=10, decimal_places=6, null=True, blank=True)
longitude = models.DecimalField(max_digits=10, decimal_places=6, null=True, blank=True)
point = models.PointField(null=True, geography=True)
def distance_from_target(self, target_lat, target_lon):
if not target_lat or not target_lon:
return None
instance_point = (self.latitude, self.longitude)
target_point = (target_lat, target_lon)
return vincenty(instance_point, target_point).kilometers
答案 0 :(得分:0)
您不需要乘以半径* 2!
我也面临postgres / postgis计算的距离与geopy.distance.vincenty
的距离之间的差异,但非常小(米级而不是公里)
我像这样查询
from django.contrib.gis.measure import Distance
from django.contrib.gis.db.models.functions import Distance as DistanceFun
from django.contrib.gis.geos import fromstr
user_location = fromstr(
"POINT({value_lon} {value_lat})".format(value_lon=value_lon, value_lat=value_lat)
)
qs.filter(
location__distance_lte=(user_location, Distance(m=value_radius_in_meters))
).annotate(
distance=DistanceFun('location', user_location)
).order_by('distance')