Gibt es in PostGIS eine andere Überblendungsfunktion als st_union?

22

Ich suche nach einer Funktion, um gemeinsame Grenzen zwischen Polygon-Features in einer Tabelle aufzulösen. ST_UNION () macht fast das, wonach ich suche, aber es erzeugt ein Multipolygon aus allen Polygonen in der Ebene, unabhängig davon, ob sie eine gemeinsame Grenze haben oder nicht. Ich würde lieber nur Grenzen zwischen Polygonen auflösen, die sich berühren. Ich dachte, es sollte eine Möglichkeit geben, ST_TOUCHES () zu verwenden, aber dann scheint die Notwendigkeit einer Überblendungsfunktion so weit verbreitet zu sein, dass ich überrascht wäre, wenn es keine eingebaute Funktion gibt, um dies zu erreichen.

Der Anwendungsfall sieht folgendermaßen aus: Ich habe Corine Landcover-Daten für ein großes europäisches Land heruntergeladen und möchte Grenzen zwischen verschiedenen Waldtypen auflösen (ca. 75.000 Polygone in einer Tabelle). Ich habe ST_UNION ausprobiert, aber es schlägt fehl mit einem "out of memory" -Fehler (30.000 Polygone haben jedoch funktioniert):

create table corine00 as 
  select st_union(the_geom) as the_geom, 
         sum(area_ha) as area_ha,
         substr(code_00,1,2) as code_00
  from clc00_c31_forests
  group by substr(code_00,1,2)

Hinweis: Alle Gesamtstrukturcodes beginnen mit '31' und ich verwende PostGIS 1.4, GEOS-Version: 3.2.0-CAPI-1.6.0

Underdunkel
quelle

Antworten:

21

ST_MemUnion () führt einen naiven und langsamen speicherfreundlichen Prozess aus. Sie können versuchen, Ihr Problem in angemessener Zeit zu lösen, wenn es klein genug ist. Sie können Ihr Problem auch einfach in Hälften aufteilen und dann die Hälften zusammenführen. Da die Ergebnisse viel weniger Punkte als die Eingaben haben, können Sie möglicherweise das gesamte Problem auf diese Weise in den Speicher einpassen. Oder verwenden Sie die schnelle speicherhungrige Routine für die Hälften und die langsamere Routine für die endgültige Zusammenführung.

Paul Ramsey
quelle
4
Es ist fantastisch, Sie hier zu haben, Paul. Danke, dass Sie unvergleichliches Fachwissen mitgebracht haben.
Uhr
1
Danke, mein Problem scheint nicht klein genug zu sein. ST_MemUnion () läuft jetzt seit 24 Stunden. Ich werde versuchen, das Problem aufzuteilen.
Underdunkel
5

Ich glaube, ST_Dump ist das, was Sie wollen:

ST_Dump :

Gibt eine Reihe von geometry_dump-Zeilen (geom, path) zurück, aus denen eine Geometrie g1 besteht. Sie kann beispielsweise zum Erweitern von MULTIPOLYGONS in POLYGONS verwendet werden. ...

Also für deinen Fall:

 SELECT (ST_Dump( ST_Union( the_geom ) )).geom
 FROM clc00_c31_forests
 GROUP BY substr(code_00,1,2)

Ich bin nicht sicher, wie es mit der Tabellenerstellung, die Sie versuchen, interagieren wird, aber es sollte Ihnen die Geometrien als separate Einträge geben. Anschließend können Sie eine räumliche Verknüpfung (mithilfe von && und ST_Contains) zwischen den beiden Tabellen ausführen, um die Daten für die Geometrien zu erfassen.

yhw42
quelle
2
Hinweis: Dies ist nur hilfreich, wenn Sie die Speicherprobleme der ST_Union behandeln! :)
yhw42
4

Ist Ihr PostGIS gegen GEOS 3.1.0+ kompiliert? Für diese Version wurde eine viel schnellere kaskadierte Vereinigung implementiert, aber wenn sie nicht gefunden wird, wird der ältere Code verwendet, der um Größenordnungen langsamer ist.

Update : Es sieht so aus, als ob Ihr PostGIS den kaskadierten Vereinigungsansatz verwendet, aber der Speichermangel ist real. Ich würde versuchen, den verfügbaren Speicher für Ihre Postgres-Instanz zu erhöhen. Hier einige Ratschläge aus Paul Ramseys FOSS4G PostGIS-Vortrag von 2007 :

  • Der Datenträgerzugriff ist langsam, sodass eine höhere Leistung erzielt werden kann, wenn mehr Speicher zum Zwischenspeichern von Daten verwendet wird!
    • Erhöhen, ansteigen shared_buffers
    • Physischer RAM - Betriebssystem benötigt * 75%
  • Das Sortieren ist schneller im Speicher
    • Erhöhen, ansteigen work_mem
  • Die Datenträgerbereinigung erfolgt schneller mit mehr Arbeitsspeicher
    • Erhöhen, ansteigen maintenance_work_mem
  • Wird pro Verbindung zugewiesen
  • Ebenfalls
    • Erhöhen, ansteigen wal_buffers
    • Erhöhen, ansteigen checkpoint_segments
    • Verringern random_page_cost

In Ihrem Fall würde ich versuchen zu erhöhen shared_buffers, die allgemeine Empfehlung ist 25% des verfügbaren Speichers für einen Datenbankserver, aber versuchen Sie, ihn auf das 3-4-fache seines aktuellen Werts zu erhöhen und zu prüfen, ob er abgeschlossen ist.

scw
quelle
postgis_geos_version () gibt zurück: 3.2.0-CAPI-1.6.0 ... Ich denke, das ist in Ordnung. Ich werde ST_Collect versuchen, danke.
Underdunkel
Nun, ST_Collect scheint keine Grenzen aufzulösen und schafft auch ein riesiges Multipolygon.
Underdunkel
Ja, ich habe die Seite für ST_Collect falsch gelesen. Ich habe meine Antwort aktualisiert, um spezifischere Ratschläge zum Optimieren der Speichernutzung von Postgres zu geben.
scw