CG_Simplify — Reduces the complexity of a geometry while preserving essential features and Z/M values.
geometry CG_Simplify(geometry geom, double precision threshold, boolean preserveTopology = false);
Simplifies a geometry using SFCGAL's simplification algorithm, which reduces the number of points or vertices while preserving the essential features of the geometry. This function preserves Z and M values during simplification.
The algorithm is based on constrained triangulation and uses the CGAL Polyline Simplification 2 library with additional handling to preserve Z and M coordinates. When topology is preserved and geometries intersect, Z and M values are interpolated at intersection points.
This function works well with 3D terrain-like geometries (2.5D) but is not designed for vertical surfaces like walls.
Availability: 3.6.0 - requires SFCGAL >= 2.1.0
This method needs SFCGAL backend.
This function supports 3d and will not drop the z-index.
This function supports M coordinates.
geom
Input geometry
threshold
Maximum distance threshold (in geometry unit) for simplification. The higher this value, the more simplified the resulting geometry will be.
preserveTopology
If set to true, the function ensures that the topology of the geometry is preserved. When geometries intersect in this mode, Z and M values at intersection points are interpolated. The default value is false.
Returns a simplified geometry with preserved Z and M values.
This example simplifies a polygon with a threshold of 0.5.
SELECT CG_Simplify(
'POLYGON((0 0,0 1,0.1 1,0.2 1,0.3 1,0.4 1,0.5 1,1 1,1 0,0 0))',
0.5
);
POLYGON((0 0,0 1,1 1,1 0,0 0))
Preserving topology can keep additional support points in a mixed ZM collection.
SELECT CG_Simplify(
'GEOMETRYCOLLECTION ZM(
LINESTRING ZM(-1 -1 3 4,0 0 10 100,1 1 20 200,0 2 15 150,0 5 30 300,2 19 25 250,-4 20 15 150),
POLYGON ZM((0 0 10 100,1 1 20 200,0 2 15 150,0 5 30 300,2 19 25 250,-4 20 15 150,0 0 10 100))
)',
2,
false
);
GEOMETRYCOLLECTION ZM (LINESTRING ZM (-1 -1 3 4,2 19 25 250,-4 20 15 150),POLYGON ZM ((0 0 10 100,2 19 25 250,-4 20 15 150,0 0 10 100)))
The topology-preserving variant keeps the shared anchor point at the collection intersection.
SELECT CG_Simplify(
'GEOMETRYCOLLECTION ZM(
LINESTRING ZM(-1 -1 3 4,0 0 10 100,1 1 20 200,0 2 15 150,0 5 30 300,2 19 25 250,-4 20 15 150),
POLYGON ZM((0 0 10 100,1 1 20 200,0 2 15 150,0 5 30 300,2 19 25 250,-4 20 15 150,0 0 10 100))
)',
2,
true
);
GEOMETRYCOLLECTION ZM (LINESTRING ZM (-1 -1 3 4,0 0 10 100,2 19 25 250,-4 20 15 150),POLYGON ZM ((0 0 10 100,2 19 25 250,-4 20 15 150,0 0 10 100)))
Compare simplification with and without topology preservation, using a threshold of 50.
WITH data AS (
SELECT ST_GeomFromText('GEOMETRYCOLLECTION(
POLYGON((88.46 158.85,90.77 171.54,147.31 173.85,146.15 145,173.85 119.62,146.15 103.46,112.69 118.46,91.92 93.08,65.38 101.15,34.23 121.92,41.15 142.69,49.23 143.85,88.46 158.85)),
POLYGON((112.69 118.46,146.15 103.46,190 60.77,185.38 43.46,126.54 26.15,83.85 28.46,67.69 64.23,43.46 58.46,10 83.85,34.23 121.92,65.38 101.15,91.92 93.08,112.69 118.46)))
') AS geom
)
SELECT geom AS input_geometry,
CG_Simplify(geom, 50, true) AS topology_preserved,
CG_Simplify(geom, 50, false) AS topology_not_preserved
FROM data;
GEOMETRYCOLLECTION(POLYGON((88.46 158.85,90.77 171.54,147.31 173.85,146.15 145,173.85 119.62,146.15 103.46,112.69 118.46,91.92 93.08,65.38 101.15,34.23 121.92,41.15 142.69,49.23 143.85,88.46 158.85)), POLYGON((112.69 118.46,146.15 103.46,190 60.77,185.38 43.46,126.54 26.15,83.85 28.46,67.69 64.23,43.46 58.46,10 83.85,34.23 121.92,65.38 101.15,91.92 93.08,112.69 118.46))) | GEOMETRYCOLLECTION(POLYGON((88.46 158.85,147.31 173.85,146.15 103.46,112.69 118.46,34.23 121.92,88.46 158.85)), POLYGON((112.69 118.46,146.15 103.46,185.38 43.46,10 83.85,34.23 121.92,112.69 118.46))) | GEOMETRYCOLLECTION(POLYGON((88.46 158.85,173.85 119.62,34.23 121.92,88.46 158.85)), POLYGON((112.69 118.46,190 60.77,10 83.85,112.69 118.46)))