I'm trying to create double-sided buffers along road segments by making a buffer and then cutting the buffer with the road segment with ST_Split()

Almost there, but for some reason not all polygons get cut: enter image description here enter image description here (The red lines are the original road network.)

All of the ones that don't work seem to have those little 'artifacts' from the buffer (lower corner of the polygon), where the buffer intersects itself.

My queries:

SELECT vl.gid, vl.rlid, ak.kommunnamn, ak.lansnamn, vl.geom
FROM vagnet AS vl, ak_riks AS ak
WHERE ST_within(vl.geom, ak.geom) AND ak.kommunnamn = 'Vaxholm';

SELECT gid, rlid, kommunnamn, lansnamn, ST_buffer(geom, 15, 'endcap=flat join=mitre quad_segs=2') AS geom
FROM vaxholm;

SELECT  vl.gid as gid,
    vl.rlid as rlid,
    vl.kommunnamn as kommunnamn,
    vl.lansnamn as lansnamn,
    ST_split(buffer.geom, ST_linemerge(vl.geom)) as geom_collection
FROM vaxholm as vl, buffer
WHERE vl.gid = buffer.gid;

SELECT (ST_dump(geom_collection)).geom as geom, gid, rlid
FROM split;

My system:

OS: Windows 10
PostgreSQL: 9.6.2
PostGIS: 2.3.2

So I ended up sort of solving the issue like this:

  CREATE TABLE buffdiff AS
    SELECT gid, rlid, kommunnamn, lansnamn,
                ST_Buffer(vl.geom, 15, 'endcap=flat join=mitre quad_segs=2'),
                ST_Buffer(vl.geom, 0.001, 'endcap=flat join=mitre quad_segs=2')
        )).geom as geom
                vagnet.gid, vagnet.rlid, ak.kommunnamn, ak.lansnamn, vagnet.geom
                FROM vagnet, ak_riks AS ak
                WHERE ST_within(vagnet.geom, ak.geom) AND ak.kommunnamn = 'Vaxholm'
            ) as vl;
  1. Create the buffer I want for the road segment.

  2. Create a very small buffer for the road segment (here 1 mm).

  3. Get the difference between them, i.e. remove the small buffer from the other.

Combined with a flat endcap, each buffer ends up consisting of two separate polygons.

I won't mark this as correct, as it doesn't really answer my initial question. I'm just documenting it as the solution I ended up going with.

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service, privacy policy and cookie policy

Not the answer you're looking for? Browse other questions tagged or ask your own question.