Welcher Datentyp für Längen- und Breitengrad?

154

Ich bin Neuling bei PostgreSQL und PostGIS. Ich möchte Breiten- und Längengrade in der PostgreSQL 9.1.1-Datenbanktabelle speichern. Ich werde die Entfernung zwischen zwei Punkten berechnen und anhand dieser Positionswerte nähere Punkte finden.

Welchen Datentyp soll ich für Längen- und Breitengrad verwenden?

user1008404
quelle
4
Wenn Sie zwei Punkte machen (2D-Lat / Lon-Karte), würde ich den Geometrie-Datentyp verwenden. Wenn Sie die Höhe oder Krümmung der Erde in Ihre Entfernungsberechnungen einbeziehen müssen, ist Geografie genau das Richtige für Sie.
Zwölfter
4
Hat eine der folgenden Antworten Ihre Frage beantwortet? Wenn ja, ermutige ich Sie, eine als Antwort auszuwählen :)
Volte

Antworten:

140

Sie können den Datentyp verwenden point- Mähdrescher, (x,y)die Ihr Lat / Long sein können. Belegt 16 Bytes: 2 float8Nummern intern.

Oder machen Sie es zwei Spalten vom Typ float(= float8oder double precision). Jeweils 8 Bytes.
Oder real(= float4), wenn keine zusätzliche Genauigkeit erforderlich ist. Jeweils 4 Bytes.
Oder auch numericwenn Sie absolute Präzision brauchen. 2 Bytes für jede Gruppe von 4 Ziffern plus 3 - 8 Bytes Overhead.

Lesen Sie das feine Handbuch über numerische Typen und geometrische Typen .


Die Datentypen geometryund geographywerden vom Zusatzmodul PostGIS bereitgestellt und belegen eine Spalte in Ihrer Tabelle. Jeder belegt 32 Bytes für einen Punkt. Es gibt einen zusätzlichen Overhead wie bei einer SRID. Diese Typen speichern (long / lat), nicht (lat / long).

Lesen Sie hier das PostGIS-Handbuch .

Erwin Brandstetter
quelle
5
Ich würde die Verwendung des floatDatentyps nicht empfehlen . Dies macht die Berechnung mit den Koordinaten sehr kompliziert. Sie sollten PostGIS und den geographyDatentyp für solche Berechnungen verwenden.
m13r
8
Es ist wirklich ein gutes Handbuch, nicht wahr? Ein leuchtendes Beispiel in der Dokumentation.
Otocan
1
Wäre es schneller, Long, Lat und Geog zu speichern, als Geog für das ursprüngliche Long Lat zu analysieren?
Dan
1
@ Dan: Kommt drauf an. Bitte stellen Sie eine neue Frage mit Details. Sie können jederzeit einen Link zu diesem für den Kontext erstellen. Kommentare sind nicht der Ort für neue Fragen.
Erwin Brandstetter
39

In PostGIS gibt es für Punkte mit Längen- und Breitengrad einen geografischen Datentyp.

So fügen Sie eine Spalte hinzu:

alter table your_table add column geog geography;

So fügen Sie Daten ein:

insert into your_table (geog) values ('SRID=4326;POINT(longitude latitude)');

4326 ist eine räumliche Referenz-ID, die angibt, dass es sich um Daten in Längen- und Breitengraden handelt, genau wie bei GPS. Mehr dazu: http://epsg.io/4326

Reihenfolge ist Längengrad, Breitengrad - wenn Sie es also als Karte zeichnen, ist es (x, y).

Um den nächstgelegenen Punkt zu finden, müssen Sie zuerst einen räumlichen Index erstellen:

create index on your_table using gist (geog);

und dann fordern Sie beispielsweise 5 an, die einem bestimmten Punkt am nächsten liegen:

select * 
from your_table 
order by geog <-> 'SRID=4326;POINT(lon lat)' 
limit 5;
Darafei Praliaskouski
quelle
1
Klarstellung Die SRID 4326 möchte den Längen- und Breitengrad in dieser Reihenfolge. Die PostGIS-Interpretation von SRID 4326 möchte jedoch einen Längen- und Breitengrad in dieser Reihenfolge. Das Beispiel ist für die Verwendung von PostGIS korrekt. postgis.net/2013/08/18/tip_lon_lat
hahmed
25

Ich befürworte nachdrücklich PostGis . Es ist spezifisch für diese Art von Datentyp und verfügt über sofort einsatzbereite Methoden zur Berechnung der Entfernung zwischen Punkten sowie über andere GIS-Vorgänge, die Sie in Zukunft als nützlich erachten können

tvieira
quelle
5

Wenn Sie nicht alle Funktionen von PostGIS benötigen, bietet Postgres (heutzutage) ein Erweiterungsmodul namens Erdabstand an . Es wird der Punkt oder Würfel verwendet - Datentyp auf Ihrer Genauigkeit Anforderungen für Abstandsberechnungen abhängig.

Mit der Funktion earth_box können Sie jetzt beispielsweise Punkte in einer bestimmten Entfernung von einem Ort abfragen.

Hans Bouwmeester
quelle
2

In PostGIS wird Geometrie gegenüber Geographie (Round-Earth-Modell) bevorzugt, da die Berechnungen viel einfacher und daher schneller sind. Es hat auch VIELE mehr verfügbare Funktionen, ist aber über sehr große Entfernungen weniger genau.

Importieren Sie Ihre CSV in lange Lat-Felder in DECIMAL(10,6)Spalten. 6 Stellen sind 10 cm genau und sollten für die meisten Anwendungsfälle ausreichend sein.

Dann wandeln Sie Ihre importierten Daten um

SELECT 
    --ST_SetSRID(ST_Point(long, lat),4326) geom -- the wrong way because SRID not set in geometry_columns table
    ST_Point(long, lat)::geometry(Geometry, 4326) geom
INTO target_table
FROM source_table;

Stellen Sie sicher, dass die SRID nicht Null ist!

SELECT * FROM public.geometry_columns WHERE f_table_name = 'target_table';

Überprüfen Sie die Reihenfolge Ihres Long Lat-Parameters mit einem WKT-Viewer und ST_AsEWKT(target_table.geom).

Indizieren Sie es dann für die beste Leistung

CREATE INDEX idx_target_table_geom_gist
    ON target_table USING gist(geom);
Golfalot
quelle