Name

ST_MakePolygon — Erzeugt ein Polygon aus einer Schale und einer optionalen Liste von Löchern.

Synopsis

geometry ST_MakePolygon(geometry linestring);

geometry ST_MakePolygon(geometry outerlinestring, geometry[] interiorlinestrings);

Beschreibung

Erzeugt ein Polygon, das durch die gegebene Hülle gebildet wird. Die Eingabegeometrie muss aus geschlossenen Linienzügen bestehen.

Variante 1: Akzeptiert eine Shell LineString.

Variante 2: Akzeptiert einen Shell LineString und ein Array von inneren (Loch) LineStrings. Ein Geometrie-Array kann mit den PostgreSQL-Konstrukten array_agg(), ARRAY[] oder ARRAY() erstellt werden.

[Note]

Diese Funktion akzeptiert keine MULTILINESTRINGs. Verwenden Sie bitte ST_LineMerge oder ST_Dump um Linienzüge zu erzeugen.

Diese Funktion unterstützt 3d und lässt den Z-Index nicht fallen.

Beispiele: Verwendung der Feld-Version

Erzeugt einen LineString aus einem codierten Linienzug.

SELECT ST_MakePolygon( ST_GeomFromText('LINESTRING(75 29,77 29,77 29, 75 29)'));

Erstellen Sie ein Polygon aus einem offenen LineString, indem Sie ST_StartPoint und ST_AddPoint verwenden, um es zu schließen.

SELECT ST_MakePolygon( ST_AddPoint(foo.open_line, ST_StartPoint(foo.open_line)) )
FROM (
  SELECT ST_GeomFromText('LINESTRING(75 29,77 29,77 29, 75 29)') As open_line) As foo;

Erzeugt einen LineString aus einem codierten Linienzug.

SELECT ST_AsEWKT( ST_MakePolygon( 'LINESTRING(75.15 29.53 1,77 29 1,77.6 29.5 1, 75.15 29.53 1)'));

st_asewkt
-----------
POLYGON((75.15 29.53 1,77 29 1,77.6 29.5 1,75.15 29.53 1))

Erstellen eines Polygons aus einem LineString mit Maßen

SELECT ST_AsEWKT( ST_MakePolygon( 'LINESTRINGM(75.15 29.53 1,77 29 1,77.6 29.5 2, 75.15 29.53 2)' ));

st_asewkt
----------
POLYGONM((75.15 29.53 1,77 29 1,77.6 29.5 2,75.15 29.53 2))

Beispiele: Außenhülle mit inneren Ringen

Erzeugung eines Donuts mit einem Ameisenloch

SELECT ST_MakePolygon( ST_ExteriorRing( ST_Buffer(ring.line,10)),
        ARRAY[  ST_Translate(ring.line, 1, 1),
                ST_ExteriorRing(ST_Buffer(ST_Point(20,20),1)) ]
        )
FROM (SELECT ST_ExteriorRing(
        ST_Buffer(ST_Point(10,10),10,10)) AS line ) AS ring;

Erstellen Sie einen Satz von Provinzgrenzen mit Löchern, die Seen darstellen. Die Eingabe ist eine Tabelle mit Provinz-Polygonen/MultiPolygonen und eine Tabelle mit Wasserlinien. Die Linien, die Seen bilden, werden mit ST_IsClosed ermittelt. Das Provinzlinienwerk wird mit ST_Boundary extrahiert. Wie von ST_MakePolygon gefordert, wird die Begrenzung mit ST_LineMerge zu einem einzigen LineString gezwungen. (Beachten Sie jedoch, dass dies ein ungültiges Polygon ergibt, wenn eine Provinz mehr als eine Region oder Inseln hat). Die Verwendung eines LEFT JOIN stellt sicher, dass alle Provinzen einbezogen werden, auch wenn sie keine Seen haben.

[Note]

Das Konstrukt mit CASE wird verwendet, da die Übergabe eines NULL-Feldes an ST_MakePolygon NULL ergibt.

SELECT p.gid, p.province_name,
        CASE WHEN array_agg(w.geom) IS NULL
        THEN p.geom
        ELSE  ST_MakePolygon( ST_LineMerge(ST_Boundary(p.geom)),
                        array_agg(w.geom)) END
FROM
        provinces p LEFT JOIN waterlines w
                ON (ST_Within(w.geom, p.geom) AND ST_IsClosed(w.geom))
GROUP BY p.gid, p.province_name, p.geom;

Eine andere Technik besteht darin, eine korrelierte Unterabfrage und den ARRAY()-Konstruktor zu verwenden, der einen Zeilensatz in ein Array umwandelt.

SELECT p.gid,  p.province_name,
    CASE WHEN EXISTS( SELECT w.geom
        FROM waterlines w
        WHERE ST_Within(w.geom, p.geom)
        AND ST_IsClosed(w.geom))
    THEN ST_MakePolygon(
        ST_LineMerge(ST_Boundary(p.geom)),
        ARRAY( SELECT w.geom
            FROM waterlines w
            WHERE ST_Within(w.geom, p.geom)
            AND ST_IsClosed(w.geom)))
    ELSE p.geom
    END AS geom
FROM provinces p;