2009-07-10 2 views
5

Wie lautet die Formel zur Berechnung der Entfernung zwischen 2 Geocodes? Ich habe einige der Antworten auf dieser Seite gesehen, aber sie sagen im Grunde, dass sie sich auf die Funktionen von SQL Server 08 verlassen, ich bin noch nicht auf 08. Jede Hilfe wäre willkommen.Entfernung zwischen 2 Geocodes

Antwort

-1

der Satz des Pythagoras?

+1

Leider ist die Erde nicht flach. –

+0

Es hängt von der Projektion ab, die Sie verwenden. Es gibt eine Projektion der Zustandsebene, die über relativ kurze Entfernungen sehr genau ist. Mit einer Projektion der Zustandsebene ist das Pythagoras-Theorem in Ordnung. Wenn Sie Breiten-/Längenkoordinaten verwenden, die bereits in Winkeln ausgedrückt sind (keine Abstände), können Sie das Pythogoräische Theorem nicht verwenden. –

0

Sie suchen nach der Länge des Great Circle Path zwischen zwei Punkten auf einer Kugel. Versuchen Sie, bei Google nach "Großkreis-Pfad" oder "Großkreis-Entfernung" zu suchen.

0

Sorry, ich weiß nicht, in welchem ​​Land Sie gerade sind. Sprechen wir über Easting und Northings (UK, Ordance Survey System) oder Lat/Long oder ein anderes System? Wenn wir Eastern und Northing sprechen, dann können Sie sqr ((x1-x2)^2 + (y1-y2)^2)
Dies erlaubt nicht für die Tatsache, dass die Erde eine Kugel ist, aber für kurze Wege werden Sie nicht bemerken. Wir verwenden es bei der Arbeit für Entfernungen zwischen Punkten innerhalb der Grafschaft.
Seien Sie vorsichtig, wie lange die Gitterreferenz verwendet wird. Ich denke, eine 8-stellige Referenz gibt Ihnen eine Distanz in Metern. Ich werde in der nächsten Woche eine definitive Antwort auf die Arbeit bekommen, wenn niemand anders es geliefert hat.

0

Das Pythagoras Theorem, wie es hier von anderen angeboten wird, funktioniert nicht so gut.

Die beste, einfache Antwort ist, die Erde als eine Kugel anzunähern (es ist eigentlich eine leicht abgeflachte Kugel, aber das ist sehr nahe). In Haskell, zum Beispiel könnten Sie die folgende verwenden, aber die Mathematik kann in so ziemlich alles transkribiert werden:

distRadians (lat1,lon1) (lat2,lon2) = 
    radius_of_earth * 
    acos (cos lat1 * cos lon1 * cos lat2 * cos lon2 + 
      cos lat1 * sin lon1 * cos lat2 * sin lon2 + 
      sin lat1 * sin lat2) where 
    radius_of_earth = 6378 -- kilometers 


distDegrees a b = distRadians (coord2rad a) (coord2rad b) where 
    deg2rad d = d * pi/180 
    coord2rad (lat,lon) = (deg2rad lat, deg2rad lon) 

distRadians erfordert Ihre Winkel in Radiant angegeben werden.

distDegrees ist eine Hilfsfunktion, die Breitengrade und Längengrade in Grad annehmen kann.

Weitere Informationen zur Ableitung dieser Formel finden Sie unter this series of posts.

Wenn Sie wirklich die zusätzliche Präzision durch die Annahme, die Erde gewährt müssen elliptisch finden Sie in diesem FAQ: http://www.movable-type.co.uk/scripts/gis-faq-5.1.html

2

Dieses es für Sie in C# tun.

Im Namespace setzen diese:

public enum DistanceType { Miles, Kilometers }; 

public struct Position 
{ 
    public double Latitude; 
    public double Longitude; 
} 

class Haversine 
{ 

    public double Distance(Position pos1, Position pos2, DistanceType type) 
    { 
     double preDlat = pos2.Latitude - pos1.Latitude; 
     double preDlon = pos2.Longitude - pos1.Longitude; 
     double R = (type == DistanceType.Miles) ? 3960 : 6371; 
     double dLat = this.toRadian(preDlat); 
     double dLon = this.toRadian(preDlon); 
     double a = Math.Sin(dLat/2) * Math.Sin(dLat/2) + 
     Math.Cos(this.toRadian(pos1.Latitude)) * Math.Cos(this.toRadian(pos2.Latitude)) * 
     Math.Sin(dLon/2) * Math.Sin(dLon/2); 
     double c = 2 * Math.Asin(Math.Min(1, Math.Sqrt(a))); 
     double d = R * c; 
     return d; 
    } 

    private double toRadian(double val) 
    { 
     return (Math.PI/180) * val; 
    } 

Dann werden diese in den Hauptcode zu verwenden:

Position pos1 = new Position(); 
        pos1.Latitude = Convert.ToDouble(hotelx.latitude); 
        pos1.Longitude = Convert.ToDouble(hotelx.longitude); 
        Position pos2 = new Position(); 
        pos2.Latitude = Convert.ToDouble(lat); 
        pos2.Longitude = Convert.ToDouble(lng); 
        Haversine calc = new Haversine(); 

        double result = calc.Distance(pos1, pos2, DistanceType.Miles); 
2

Wenn

  • Sie wissen, dass die zwei Punkte sind „nicht zu weit voneinander entfernt "
  • und Sie tolerieren eine "einigermaßen kleine" Fehler.

Dann betrachten, daß die Erde zwischen den Punkten 2 flach ist:

  • Der Entfernungsunterschied in der Breitenrichtung ist EarthRadius * latitude difference
  • Der Entfernungsunterschied in der Längenrichtung EarthRadius * longitude difference * cos(latitude) ist. Wir multiplizieren mit cos(lat), weil die Längengrade nicht den gleichen km Abstand machen, wenn sich der Breitengrad ändert. Als P1 und P2 nahe sind, cos (latP1) liegt in der Nähe von cos (latP2)
  • Dann Pythagore

In JavaScript:

function ClosePointsDistance(latP1, lngP1, latP2, lngP2) { 
    var d2r = Math.PI/180, 
    R=6371; // Earth Radius in km 
    latP1 *= d2r; lngP1 *= d2r; latP2 *= d2r; lngP2 *= d2r; // convert to radians 
    dlat = latP2 - latP1, 
    dlng = (lngP2 - lngP1) * Math.cos(latP1); 
    return R * Math.sqrt(dlat*dlat + dlng*dlng); 
} 

ich es zwischen Paris getestet und Orleans (Frankreich): die Formel findet 110,9 km, während die (exakte) Haversine Formel 111,0 km findet.

!!! Hüten Sie sich vor Situationen um den Meridian 0 (Sie können es verschieben): Wenn P1 bei Lng 359 und P2 bei Lng 0 ist, wird die Funktion sie als ungewöhnlich weit betrachten !!!

1

Hier ist eine Möglichkeit, es zu tun, wenn Sie SQL Server verwenden.

CREATE function dist (@Lat1 varchar(50), @Lng1 varchar(50),@Lat2 varchar(50), @Lng2 varchar(50)) 
returns float 
as 
begin 

declare @p1 geography 
declare @p2 geography 

set @p1 = geography::STGeomFromText('POINT('+ @Lng1+' '+ @Lat1 +')', 4326) 
set @p2 = geography::STGeomFromText('POINT('+ @Lng2+' '+ @Lat2 +')', 4326) 

return @p1.STDistance(@p2) 
end