¿Cuál es el mejor truco para importar grandes conjuntos de datos en PostGIS?

21

Tengo que importar grandes Shapefiles (> 1 millón de registros) en PostGIS, y me he estado preguntando cuál es la mejor manera de hacerlo.

ingrese la descripción de la imagen aquí

En mi pregunta, utilicé la palabra "piratear", en lugar de herramienta, a propósito porque creo que no se trata tanto de qué herramienta, sino de qué conjunto de pasos o configuraciones de configuración usar. Hasta ahora, he probado el complemento SPIT (QGIS), la herramienta Shp2pgsql Postgis y la herramienta GDAL ogr2ogr . Puedes ver mi reseña completa en esta publicación. Hasta ahora, encuentro que todos ellos realmente no responden, cuando se trata de un gran conjunto de datos. Me preguntaba si alguien experimentó un problema similar y si podría compartir algo sobre el enfoque.

doblebyte
fuente

Respuestas:

18

Te hice una prueba:

  • PostgreSQL 9.3
  • PostGIS 2.1
  • Windows 7
  • Procesador i7 [email protected] GHz
  • GDAL 2.0-dev de 64 bits
  • archivo de forma de 1,14 millones de polígonos, tamaño de archivo 748 MB

Comando Ogr2ogr:

ogr2ogr -f PostgreSQL PG: "dbname = 'databasename' host = 'addr' port = '5432' user = 'x' password = 'y'" test.shp --config PG_USE_COPY YES -nlt MULTIPOLYGON

Tiempo total: 1 minuto 30 segundos

usuario30184
fuente
¡Gracias por tu respuesta! Parece realmente rápido; Creo que no funcionó para mí porque no utilicé el indicador --config PG_USE_COPY YES; Me las arreglé para importarlo rápidamente usando: psql target-db -U <usuario de administrador> -p <puerto> -h <nombre de instancia de base de datos> -c "\ copy source-table de 'source-table.csv' con DELIMITER ' , '"(y luego reconstruir la geometría), que supongo que es un enfoque similar.
doublebyte
COPY es más rápido y será el predeterminado en GDAL 2.0 cuando los datos se escriben en nuevas tablas. Cuando se utilizan inserciones, el tamaño predeterminado de las transacciones (controlado con el parámetro -gt) era de solo 200 funciones antes de GDAL versión 1.11 cuando se aumentó a 20000 funciones. Las transacciones más grandes significan menos transacciones y eso puede generar una gran aceleración.
user30184
44
El uso de COPY es clave, y probablemente obtendrá una traducción aún más rápida con shp2pgsql y el distintivo -D. shp2pgsql -D test.shp | psql testdb
Paul Ramsey
Paul, ¿shp2pgsql -D es lo mismo que COPY? No está claro en los documentos que dicen que esto usa el formato de "volcado", pero no estoy seguro de lo que eso significa incluso para una operación de carga (a diferencia de una copia de seguridad / restauración). Me doy cuenta de que shp2pgsql-gui tiene la opción "Cargar datos usando COPY en lugar de INSERT", pero no tiene la opción "formato de volcado", así que ¿estoy en lo cierto al suponer que son iguales?
Lee Hachadoorian
Sí, -D es lo mismo que usar COPY.
Darrell Fuhriman
9

Después de las sugerencias del usuario 30184 , Paul Ramsey y mis propios experimentos. Decidí responder esta pregunta.

No mencioné en esta pregunta que estoy importando datos a un servidor remoto. (aunque se describe en la publicación de blog a la que me refiero). Las operaciones como las inserciones en Internet están sujetas a una latencia de red. Tal vez no sea irrelevante mencionar que este servidor está en Amazon RDS , lo que me impide enviar ssh a la máquina y ejecutar operaciones localmente.

Teniendo esto en cuenta, rediseñé mi enfoque, utilizando la directiva "\ copy" para promover un volcado de los datos en una nueva tabla. Creo que esta estrategia es una clave esencial, que también se mencionó en los comentarios / respuestas a esta pregunta.

psql database -U user -h host.eu-west-1.rds.amazonaws.com -c "\copy newt_table from 'data.csv' with DELIMITER ','"

Esta operación fue increíblemente rápida. Desde que importé un csv, tuve todo el trabajo de completar la geometría, agregar un índice espacial, etc. Todavía era notablemente rápido, ya que estaba ejecutando consultas en el servidor .

Decidí comparar también las sugerencias del usuario 30184 , Paul Ramsey . Mi archivo de datos era un archivo de forma puntual con 3035369 registros y 82 MB.

El enfoque ogr2ogr (usando la directiva PG_USE_COPY) terminó en 1:03:00 m, que todavía es * mucho mejor que antes.

El enfoque shp2pgsql (usando la directiva -D) terminó en solo 00:01:04 m.

Vale la pena decir que ogr2ogr creó un índice espacial durante la operación, mientras que shp2pgsql no lo hizo. Descubrí que es mucho más eficiente crear el índice después de realizar la importación, en lugar de aumentar la operación de importación con este tipo de solicitud.

La conclusión es: shp2pgsql, cuando está correctamente parametrizado, es extremadamente adecuado para realizar grandes importaciones, es decir, aquellas que se realizarán dentro de Amazon Web Services.

Tabla espacial con más de 3 millones de registros, importados usando shp2pgsql

Puede leer una descripción más detallada de estas conclusiones, en la actualización de esta publicación.

doblebyte
fuente
Antes de acusar a GDAL demasiado, eche un vistazo a la documentación. Ogr2ogr no está involucrado, es más bien el controlador GDAL PostGIS y tiene una opción para deshabilitar el índice espacial gdal.org/drv_pg.html . El uso con ogr2ogr es agregar -lco SPATIAL_INDEX = NO. GDAL también tiene otro controlador para PGDump que podría adaptarse mejor a su caso de uso gdal.org/drv_pgdump.html . Quizás también mencionarás estas cosas en tu blog.
user30184
1
La diferencia de velocidad 1:03:00 y 00:01:04 entre ogr2ogr y shp2pgsql es enorme. Estoy seguro de que es real, pero el resultado no puede generalizarse. Si prueba con una base de datos local de PostGIS, la diferencia será mucho menor. Su resultado significa que algo va muy mal para ogr2ogr. ¿Qué versión de GDAL usaste? Si es anterior a la versión 1.11, ¿intentó probar aumentando el tamaño de las transacciones agregando algo como -gt 60000?
user30184
1
No es una hinchazón adicional crear en el índice en la importación de lo que es hacerlo después. El comando emitido es exactamente el mismo y el tiempo que lleva exactamente el mismo. Además, si desea que shp2pgsql agregue el índice, solo necesita agregar la opción '-I'.
Darrell Fuhriman
Gracias por tus comentarios. Mi estudio de caso fue una importación a un Postgres que se ejecuta en AWS, por lo que fue importante para mí que la transacción se realizara bien en la red. Utilicé el indicador PG_USE_COPY en ogr2ogr, pero no probé el controlador PGDump, que desde la página de manual parece prometedor. Mi versión de GDAL es 1.7. Debería comparar todo en igualdad de condiciones (con o sin el índice), pero por lo que Daniel me dice, este no es el problema, ya que creo el índice bastante rápido en la base de datos ...
doublebyte
1
Sí, los estudios de caso están bien si se han escrito para que los lectores no tengan la sensación de que los resultados pueden generalizarse a lo que realmente representan. Por ejemplo, sería bueno mencionar que realizó la prueba con la versión GDAL de 5 años y que puede haber algún desarrollo, o no, desde entonces. Seguramente, su versión necesita un valor -gt mayor para un buen rendimiento, pero de todos modos no tiene mucho sentido probar con una versión GDAL anterior a la 1.10.
user30184