it-swarm.com.de

Ermitteln Sie den Abstand zwischen zwei Geo-Punkten

Ich möchte eine App erstellen, die den nächstgelegenen Ort überprüft, an dem sich ein Benutzer befindet. Ich kann leicht den Standort des Benutzers ermitteln und habe bereits eine Liste von Orten mit Längen- und Breitengrad.

Was wäre der beste Weg, um den nächstgelegenen Ort der Liste gegenüber dem aktuellen Benutzerort zu ermitteln. 

Ich konnte nichts in den Google APIs finden. 

104
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);

Referenz: http://developer.Android.com/reference/Android/location/Location.html#distanceTo(Android.location.Location)

140
praveen

http://developer.Android.com/reference/Android/location/Location.html

Schauen Sie in distanceTo oder distanceBetween. Sie können ein Location-Objekt aus einem Breiten- und Längengrad erstellen:

Location location = new Location("");
location.setLatitude(lat);
location.setLongitude(lon);
121
haseman

Eine angenäherte Lösung (basierend auf einer gleichwinkligen Projektion), viel schneller (es werden nur 1 Trigger und 1 Quadratwurzel benötigt).

Diese Annäherung ist relevant, wenn Ihre Punkte nicht zu weit voneinander entfernt sind. Es wird immer überschätzen im Vergleich zur tatsächlichen Haversinus-Entfernung. Zum Beispiel wird nicht mehr als 0,05382% zur tatsächlichen Entfernung addiert, wenn der Delta-Breiten- oder Längengrad zwischen Ihren beiden Punkten 4 Dezimalgrad nicht überschreitet.

Die Standardformel (Haversine) ist die genaue eine (das heißt, sie funktioniert für ein paar Längen-/Breitengrade auf der Erde), ist aber viel langsamer, da sie 7 trigonometrische und benötigt 2 Quadratwurzeln. Wenn einige Punkte nicht zu weit voneinander entfernt sind und die absolute Genauigkeit nicht von größter Bedeutung ist, können Sie diese ungefähre Version (Äquirectangular) verwenden, die viel schneller ist, da nur eine trigonometrische und eine Quadratwurzel verwendet werden.

// 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;

Sie können dies weiter optimieren durch entweder:

  1. Entfernen der Quadratwurzel wenn Sie einfach den Abstand mit einem anderen vergleichen (in diesem Fall vergleichen Sie beide quadratischen Abstände);
  2. Ausklammern des Cosinus wenn Sie den Abstand von einem Hauptpunkt zu vielen anderen berechnen (in diesem Fall führen Sie die gleichwinklige Projektion zentriert auf den Hauptpunkt durch, sodass Sie den Cosinus für alle Vergleiche einmal berechnen können) .

Weitere Informationen finden Sie unter: http://www.movable-type.co.uk/scripts/latlong.html

Es gibt eine nette Referenzimplementierung der Haversine-Formel in mehreren Sprachen unter: http://www.codecodex.com/wiki/Calculate_Distance_Between_Two_Points_on_a_Globe

30

Es gibt einige Methoden, die Sie verwenden können. Um jedoch herauszufinden, welche der besten Methoden ist, müssen Sie zunächst wissen, ob Sie die Höhe des Benutzers sowie die Höhe der anderen Punkte kennen.

Abhängig von der Genauigkeit, nach der Sie suchen, können Sie entweder die Formeln von Haversine oder Vincenty betrachten ...

Auf diesen Seiten werden die Formeln detailliert beschrieben, und für weniger mathematisch Interessierte wird erklärt, wie Sie sie in Skripts implementieren können!

Haversine Formula: http://www.movable-type.co.uk/scripts/latlong.html

Vincenty Formula: http://www.movable-type.co.uk/scripts/latlong-vincenty.html

Wenn Sie Probleme mit einer der Bedeutungen in den Formeln haben, kommentieren Sie sie einfach und ich werde mein Bestes tun, um sie zu beantworten :)

10
Dwaine Bailey

Es gibt zwei Möglichkeiten, um die Entfernung zwischen LatLng zu ermitteln.

public static void distanceBetween (double startLatitude, double startLongitude, double endLatitude, double endLongitude, float[] results)

Sieh dir das an

und zweitens

public float distanceTo (Location dest) wie von praveen geantwortet.

3
Xar E Ahmer
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];
    }
2
Levon Petrosyan

Verwenden Sie einfach die folgende Methode, geben Sie es lat und long und erhalten Sie eine Distanz in Metern:

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;
}
0
farhad.kargaran

sie können mit Google Map API Entfernung und Zeit berechnen Google Map API

Übergeben Sie einfach heruntergeladene JSON-Daten an diese Methode, um Echtzeit-Distanz und -Zeit zwischen zwei Latlongs zu erhalten 

void parseJSONForDurationAndKMS(String json) throws JSONException {

    Log.d(TAG, "called parseJSONForDurationAndKMS");
    JSONObject jsonObject = new JSONObject(json);
    String distance;
    String duration;
    distance = jsonObject.getJSONArray("routes").getJSONObject(0).getJSONArray("legs").getJSONObject(0).getJSONObject("distance").getString("text");
    duration = jsonObject.getJSONArray("routes").getJSONObject(0).getJSONArray("legs").getJSONObject(0).getJSONObject("duration").getString("text");

    Log.d(TAG, "distance : " + distance);
    Log.d(TAG, "duration : " + duration);

    distanceBWLats.setText("Distance : " + distance + "\n" + "Duration : " + duration);


}
0
saigopi