android - medir - Obtener la distancia entre dos puntos geográficos
geolocalizacion android studio google maps (7)
Quiero hacer una aplicación que verifique cuál es el lugar más cercano desde donde se encuentra el usuario. Puedo obtener fácilmente la ubicación del usuario y tengo una lista de lugares con latitud y longitud.
Cuál sería la mejor manera de saber el lugar más cercano de la lista contra la posición actual.
No pude encontrar nada en las API de Google.
Me preocupa que deba recurrir a mi cálculo y tener que hacer cálculos para calcularlo.
Qué piensan ustedes ?
Saludos y gracias por leer o responder.
Hay dos formas de obtener distancia entre LatLng.
public static void distanceBetween (double startLatitude, double startLongitude, double endLatitude, double endLongitude, float[] results)
y segundo
public float distanceTo (Location dest)
respondido por praveen.
Hay un par de métodos que podría usar, pero para determinar cuál es el mejor, primero debemos saber si conoce la altitud del usuario, así como la altitud de los otros puntos.
Dependiendo del nivel de precisión que esté buscando, podría examinar las fórmulas de Haversine o Vincenty ...
Estas páginas detallan las fórmulas y, para las menos inclinadas matemáticamente, ¡también proporcionan una explicación de cómo implementarlas en el script!
Haversine Formula: http://www.movable-type.co.uk/scripts/latlong.html
Vincenty Formula: http://www.movable-type.co.uk/scripts/latlong-vincenty.html
Si tiene algún problema con alguno de los significados de las fórmulas, simplemente coméntelo y haré todo lo posible para responderlas :)
Solo usa el siguiente método, pásalo lat y long y obtén distancia en el medidor:
private static double distance_in_meter(final double lat1, final double lon1, final double lat2, final double lon2) {
double R = 6371000f; // Radius of the earth in m
double dLat = (lat1 - lat2) * Math.PI / 180f;
double dLon = (lon1 - lon2) * Math.PI / 180f;
double a = Math.sin(dLat/2) * Math.sin(dLat/2) +
Math.cos(latlong1.latitude * Math.PI / 180f) * Math.cos(latlong2.latitude * Math.PI / 180f) *
Math.sin(dLon/2) * Math.sin(dLon/2);
double c = 2f * Math.atan2(Math.sqrt(a), Math.sqrt(1-a));
double d = R * c;
return d;
}
Una solución aproximada (basada en una proyección equirectangular), mucho más rápida (requiere solo 1 trig y 1 raíz cuadrada).
Esta aproximación es relevante si tus puntos no están muy separados. Siempre sobreestimará en comparación con la distancia real de haversine. Por ejemplo, agregará no más de 0.05382% a la distancia real si la latitud o longitud delta entre sus dos puntos no excede los 4 grados decimales .
La fórmula estándar (Haversine) es la exacta (es decir, funciona para cualquier par de longitud / latitud en la tierra) pero es mucho más lenta ya que necesita 7 raíces trigonométricas y 2 raíces cuadradas. Si su par de puntos no están demasiado separados, y la precisión absoluta no es primordial, puede usar esta versión aproximada (Equirectangular), que es mucho más rápida ya que usa solo una raíz trigonométrica y una raíz cuadrada.
// Approximate Equirectangular -- works if (lat1,lon1) ~ (lat2,lon2)
int R = 6371; // km
double x = (lon2 - lon1) * Math.cos((lat1 + lat2) / 2);
double y = (lat2 - lat1);
double distance = Math.sqrt(x * x + y * y) * R;
Puede optimizar esto aún más :
- Eliminar la raíz cuadrada si simplemente compara la distancia con otra (en ese caso, compare la distancia cuadrada);
- Factorizar el coseno si calcula la distancia desde un punto maestro a muchos otros (en ese caso, usted hace la proyección equirrectangular centrada en el punto maestro, para que pueda calcular el coseno una vez para todas las comparaciones).
Para obtener más información, consulte: http://www.movable-type.co.uk/scripts/latlong.html
Hay una buena implementación de referencia de la fórmula Haversine en varios idiomas en: http://www.codecodex.com/wiki/Calculate_Distance_Between_Two_Points_on_a_Globe
http://developer.android.com/reference/android/location/Location.html
Mire en distanceTo o distanceBetween. Puede crear un objeto de ubicación desde una latitud y longitud:
Location location = new Location("");
location.setLatitude(lat);
location.setLongitude(lon);
Location loc1 = new Location("");
loc1.setLatitude(lat1);
loc1.setLongitude(lon1);
Location loc2 = new Location("");
loc2.setLatitude(lat2);
loc2.setLongitude(lon2);
float distanceInMeters = loc1.distanceTo(loc2);
Referencia: http://developer.android.com/reference/android/location/Location.html#distanceTo(android.location.Location)
private float getDistance(double lat1, double lon1, double lat2, double lon2) {
float[] distance = new float[2];
Location.distanceBetween(lat1, lon1, lat2, lon2, distance);
return distance[0];
}