Puede obtener un estimador del límite superior muy rápido en distancia utilizando la distancia de Manhattan (escalado para la latitud), esto debería ser lo suficientemente bueno para rechazar el 99,9% de los candidatos si no están cerca (EDIT: desde entonces díganos que están cerca. En ese caso, su métrica debe ser de distancia al cuadrado, según el comentario de Lars H). Considere este equivalente para rechazar cualquier cosa fuera de un cuadro delimitador de rectángulo esférico (como una aproximación a un recuadro delimitador circular). no hago Rubí asi que aquí hay algoritmo con pseudocódigo:
Deje que la latitud, longitud de su punto de referencia P (pa, po) y la otro punto X (xa, xo). Precomputa ka, factor de escala de latitud para distancias longitudinales: ka (= cos (pa en °)). (Estrictamente, ka = constante es una aproximación linealizada en la proximidad de P.)
Entonces, el estimador de distancia es: D(X,P) = ka*|xa-pa| + |xo-po| = ka*da + do
donde | z | significa abs (z). En el peor de los casos, esto sobreestima la distancia real en un factor de √2 (cuando da == do), por lo tanto, lo permitimos de la siguiente manera:
Realice una búsqueda activa y mantenga Dmin, la quinta escama más pequeña-Manhattan-distance- estimar. Por lo tanto puede rechazar por adelantado todos los puntos para los que D (X, P)> √2 * Dmin (ya que deben estar al menos más lejos que √ ((ka * da) ² + do²) - eso debería eliminar el 99.9% de puntos). Guarde una lista de todos los puntos candidatos restantes con D (X, P) < = √2 * Dmin. Actualiza Dmin si encuentras una nueva quinta más pequeña D. Cola de prioridad, o bien una lista de (coord, D) son buenas estructuras de datos. Tenga en cuenta que nunca calculamos la distancia euclidiana, solo utilizamos la multiplicación y la suma flotante.
(Considere esto similar al árbol de cuatro ramas, excepto la filtración de todo, excepto la región que nos interesa, por lo tanto, no hay necesidad de calcular distancias exactas por adelantado o construir la estructura de datos.)
Sería de gran ayuda si nos dice la propagación esperada en latitudes, longitudes (grados, minutos o lo que sea) Si todos los puntos están cerca, el factor √2 en este estimador será demasiado conservador y marcará todos los puntos como candidato, un estimador de distancia basado en la tabla de búsqueda sería preferible)
Pseudocódigo:
initialize Dmin with the fifth-smallest D from the first five points in list
for point X in list:
if D(X,P) <= √2 * Dmin:
insert the tuple (X,D) in the priority-queue of candidates
if (Dmin>D): Dmin = D
# after first pass, reject candidates with D > √2 * Dmin (use the final value of Dmin)
# ...
# then a second pass on candidates to find lowest 5 exact distances
Si es que son pocos los puntos que está bien para ir de uno en uno. – Andrey
Independientemente del algoritmo que elija, puede ahorrar algo de tiempo comparando distancias cuadradas en lugar de distancias reales. No es necesario realizar operaciones de raíz cuadrada si no necesita conocer las distancias reales. –