Ordering a request for a distance relative to a given position

I have a model containing latitude and longitude information like FloatFields.

class Trader(models.Model): latitude = models.FloatField() longitude = models.FloatField() 

I would like to order this model at a greater distance from the given position (lat, lon), but it may not seem like this using F () expressions (using the haversine library, I was unable to convert them to float numbers)

 Trader.objects.all().annotate(distance=haversine((lat, lon), (float(F('latitude')), float(F('longitude'))))).order_by('distance') 

This request throws the following TypeError:

 float() argument must be a string or a number 

I also tried using ExpressionWrapper with the FloatField () argument as output_field without success.

How could I achieve this?

Thank you in advance for your help!

+4
source share
2 answers

Func is new in Django 1.8.

 from django.db.models import Func, F class Sin(Func): function = 'SIN' class Cos(Func): function = 'COS' class Acos(Func): function = 'ACOS' class Radians(Func): function = 'RADIANS' radlat = Radians(latitude) # given latitude radlong = Radians(longitude) # given longitude radflat = Radians(F('latitude')) radflong = Radians(F('longitude')) Expression = 3959.0 * Acos(Cos(radlat) * Cos(radflat) * Cos(radflong - radlong) + Sin(radlat) * Sin(radflat)) Trader.objects.annotate(distance=Expression).order_by('distance') 

Based on this post .

+2
source

Note that https://docs.djangoproject.com/en/1.8/ref/models/expressions/#f-expressions "generates SQL" and float ("generate sql") does not make sense. "generate sql" == use the value of the field in the generated sql. You will need to change the haversine function so that it knows how to translate itself to sql, which does heavy computing and is friendly with django ...

You will undoubtedly need to be creative in solving this problem. Raw sql seems to be the fastest way to get results if you can write sql to perform these calculations. Think about how to use geo extions like postgis. You might consider precomputing if you have a small and fixed set of input (lat, lon) combinations or “preliminary estimates” to be able to limit the number of query results and compute and sort in python.

0
source

All Articles