¿Qué tipo de datos para latitud y longitud?


154

Soy novato en PostgreSQL y PostGIS. Quiero almacenar valores de latitud y longitud en la tabla de base de datos PostgreSQL 9.1.1. Calcularé la distancia entre dos puntos, encontraré puntos más cercanos utilizando los valores de esta ubicación.

¿Qué tipo de datos debo usar para latitud y longitud?


44
Si está haciendo dos puntos (mapa 2D lat / lon), usaría el tipo de datos Geometry. Si necesita introducir altitud o curvatura de la tierra en sus cálculos de distancia, Geografía es donde desea ir.
Duodécimo

44
¿Alguna de las respuestas a continuación respondió a su pregunta? Si es así, te animo a que selecciones una como respuesta :)
Volte

Respuestas:


140

Puede usar el tipo de datos point: combinaciones (x,y)que pueden ser su lat / long. Ocupa 16 bytes: 2 float8números internamente.

O haga dos columnas de tipo float(= float8o double precision). 8 bytes cada uno.
O real(= float4) si no se necesita precisión adicional. 4 bytes cada uno.
O incluso numericsi necesita una precisión absoluta. 2 bytes para cada grupo de 4 dígitos, más gastos generales de 3 a 8 bytes.

Lea el excelente manual sobre tipos numéricos y tipos geométricos .


Los tipos de datos geometryy geographyson proporcionados por el módulo adicional PostGIS y ocupan una columna en su tabla. Cada uno ocupa 32 bytes para un punto. Hay algunos gastos generales adicionales como un SRID allí. Estos tipos almacenan (largo / lat), no (lat / long).

Comience a leer el manual de PostGIS aquí .


55
No recomendaría usar el floattipo de datos. Hace que el cálculo con las coordenadas sea muy complicado. Debe usar PostGIS y el geographytipo de datos para tales cálculos.
m13r

8
Realmente es un buen manual, ¿no? Un brillante ejemplo en la documentación.
otocan

1
¿Sería más rápido almacenar long, lat y geog sobre intentar analizar geog para el lat largo original?
Dan

1
@Dan: Depende. Por favor haga una nueva pregunta con detalles. Siempre puede vincular a este para el contexto. Los comentarios no son el lugar para nuevas preguntas.
Erwin Brandstetter

40

En PostGIS, para los puntos con latitud y longitud hay un tipo de datos de geografía.

Para agregar una columna:

alter table your_table add column geog geography;

Para insertar datos:

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

4326 es la ID de referencia espacial que dice que son datos en grados de longitud y latitud, igual que en el GPS. Más sobre esto: http://epsg.io/4326

El orden es Longitud, Latitud, así que si lo traza como el mapa, es (x, y).

Para encontrar el punto más cercano, primero necesita crear un índice espacial:

create index on your_table using gist (geog);

y luego solicite, digamos, 5 más cercano a un punto dado:

select * 
from your_table 
order by geog <-> 'SRID=4326;POINT(lon lat)' 
limit 5;

1
Aclaración, el SRID 4326 quiere la longitud de latitud en ese orden. Pero la interpretación de PostGIS de SRID 4326 quiere longitud latitud en ese orden. El ejemplo es correcto para el uso de PostGIS. postgis.net/2013/08/18/tip_lon_lat
hahmed

26

Abogo firmemente por PostGis . Es específico para ese tipo de datos y tiene métodos listos para usar para calcular la distancia entre puntos, entre otras operaciones SIG que puede encontrar útiles en el futuro


5

Si no necesita toda la funcionalidad que ofrece PostGIS, Postgres (hoy en día) ofrece un módulo de extensión llamado earthdistance . Utiliza el tipo de datos de punto o cubo según sus necesidades de precisión para los cálculos de distancia.

Ahora puede usar la función earth_box para, por ejemplo, consultar puntos dentro de una cierta distancia de una ubicación.


2

En PostGIS, se prefiere la Geometría sobre la Geografía (modelo de tierra redonda) porque los cálculos son mucho más simples, por lo tanto, más rápidos. También tiene MUCHAS funciones más disponibles, pero es menos preciso en distancias muy largas.

Importe su CSV a campos lat largos a DECIMAL(10,6)columnas. 6 dígitos tiene una precisión de 10 cm, debería ser suficiente para la mayoría de los casos de uso.

Luego envíe sus datos importados

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;

¡Verifique que SRID no sea cero!

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

Valide el orden de su parámetro lat largo usando un visor WKT y ST_AsEWKT(target_table.geom).

Luego indexe para obtener el mejor rendimiento

CREATE INDEX idx_target_table_geom_gist
    ON target_table USING gist(geom);
Al usar nuestro sitio, usted reconoce que ha leído y comprende nuestra Política de Cookies y Política de Privacidad.
Licensed under cc by-sa 3.0 with attribution required.