<div dir="ltr"><div dir="ltr"><br></div><div dir="ltr">My guess is this is caused by numerical precision issues. Due to numerical rounding, it is the case that the intersection of line L with polygon P does NOT necessarily lie within P. I.e. ST_Within( ST_Intersection( L, P), P ) may or may NOT be true. </div><div dir="ltr"><br></div><div dir="ltr">In general, due to numerical rounding the overlay operations are not fully consistent with the spatial predicates. There's some more information about this in the JTS FAQ [1].</div><div dir="ltr"><div><br></div><div>The reason for this is that in general it is impossible to accurately represent the intersection point of two line segments defined by floating point numbers using floating point numbers of the same precision. So the result of ST_Intersection may contain a line segment with an endpoint that falls outside the polygon. This situation is evaluated precisely by ST_Within, which thus returns false.</div><div><br></div><div>For your case, one fix is to create a new table for the initial intersections. This should not contain any lines which did not intersect the polygon. (You may also wish to filter out intersection results which are empty or of very short length, since these can theoretically occur).</div><div><br></div><div>In the future it may be possible that PostGIS provides spatial predicates which accept a distance tolerance, which should allow this issue to be handled more directly.</div><div><br></div><div>[1] <a href="https://locationtech.github.io/jts/jts-faq.html#D7">https://locationtech.github.io/jts/jts-faq.html#D7</a></div></div><br><div class="gmail_quote"><div dir="ltr" class="gmail_attr">On Thu, Aug 29, 2019 at 4:58 AM <<a href="mailto:paul.malm@lfv.se">paul.malm@lfv.se</a>> wrote:<br></div><blockquote class="gmail_quote" style="margin:0px 0px 0px 0.8ex;border-left:1px solid rgb(204,204,204);padding-left:1ex">
<div lang="SV">
<div class="gmail-m_-6210501267127694606WordSection1">
<p class="MsoNormal"><span lang="EN-US">Hi,<u></u><u></u></span></p>
<p class="MsoNormal"><span lang="EN-US">I have a layer with lines that I have buffered to a polygon layer, those polygons (not multipolygons) are unioned and containes holes.<u></u><u></u></span></p>
<p class="MsoNormal"><span lang="EN-US">I would like to create a line layer (from another line layer) with the line parts that are within buffered area in the polygon layer.<u></u><u></u></span></p>
<p class="MsoNormal"><span lang="EN-US">I’ve tried like this:<u></u><u></u></span></p>
<p class="MsoNormal"><span lang="EN-US" style="font-size:10pt;font-family:Consolas;color:rgb(42,0,255)">update linelayer b set the_geom = ST_MULTI(ST_Intersection(b.the_geom, p.the_geom)) FROM polygonlayer p WHERE ST_Intersects(b.the_geom,
p.the_geom)<u></u><u></u></span></p>
<p class="MsoNormal"><span lang="EN-US">This leaves me with the line parts inside the buffered area and all lines that had no intersection with the buffered polygons. That’s ok, but now I have to erase the lines that had no intersection with the polygons.<u></u><u></u></span></p>
<p class="MsoNormal"><span lang="EN-US">I run makevalid on the tables, to be sure<u></u><u></u></span></p>
<p class="MsoNormal"><span lang="EN-US" style="font-size:10pt;font-family:Consolas;color:rgb(42,0,255);background:rgb(232,242,254)">UPDATE polygonlayer SET the_geom = ST_Makevalid(the_geom) WHERE st_isvalid(the_geom)=false</span><span lang="EN-US" style="font-size:10pt;font-family:Consolas;color:rgb(42,0,255)"><u></u><u></u></span></p>
<p class="MsoNormal"><span lang="EN-US" style="font-size:10pt;font-family:Consolas;color:rgb(42,0,255);background:rgb(232,242,254)">UPDATE
</span><span lang="EN-US" style="font-size:10pt;font-family:Consolas;color:rgb(42,0,255)">linelayer
<span style="background:rgb(232,242,254)">SET the_geom = ST_Makevalid(the_geom) WHERE st_isvalid(the_geom)=false</span><u></u><u></u></span></p>
<p class="MsoNormal"><span lang="EN-US"><u></u> <u></u></span></p>
<p class="MsoNormal"><span lang="EN-US">I create a primary key<u></u><u></u></span></p>
<p class="MsoNormal"><span lang="EN-US" style="font-size:10pt;font-family:Consolas;color:rgb(42,0,255)">ALTER TABLE linelayer ADD COLUMN \"pkkey\" serial NOT NULL PRIMARY KEY<u></u><u></u></span></p>
<p class="MsoNormal"><span lang="EN-US"><u></u> <u></u></span></p>
<p class="MsoNormal"><span lang="EN-US">I reindex the tables, to be sure:<u></u><u></u></span></p>
<p class="MsoNormal"><span lang="EN-US" style="font-size:10pt;font-family:Consolas;color:rgb(42,0,255)">REINDEX TABLE linelayer</span><span lang="EN-US" style="font-size:10pt;font-family:Consolas"><u></u><u></u></span></p>
<p class="MsoNormal"><span lang="EN-US" style="font-size:10pt;font-family:Consolas;color:rgb(42,0,255)">REINDEX TABLE polygonlayer<u></u><u></u></span></p>
<p class="MsoNormal"><span lang="EN-US" style="font-size:10pt;font-family:Consolas"><u></u> <u></u></span></p>
<p class="MsoNormal"><span lang="EN-US">I change to LineStrings just to be sure not having several linestings in a MultiLineString
<u></u><u></u></span></p>
<p class="MsoNormal"><span lang="EN-US" style="font-size:10pt;font-family:Consolas;color:rgb(42,0,255)">CREATE TABLE dumpedlines AS SELECT *, (ST_Dump(the_geom)).geom AS the_geom2 FROM lineLayer<u></u><u></u></span></p>
<p class="MsoNormal"><span lang="EN-US" style="font-size:10pt;font-family:Consolas;color:rgb(42,0,255)">ALTER TABLE dumpedlines DROP COLUMN IF EXISTS the_geom</span><span lang="EN-US" style="font-size:10pt;font-family:Consolas"><u></u><u></u></span></p>
<p class="MsoNormal"><span lang="EN-US" style="font-size:10pt;font-family:Consolas;color:rgb(42,0,255)">ALTER TABLE dumpedlines RENAME COLUMN the_geom2 TO the_geom</span><span lang="EN-US" style="font-size:10pt;font-family:Consolas"><u></u><u></u></span></p>
<p class="MsoNormal"><span lang="EN-US" style="font-size:10pt;font-family:Consolas;color:rgb(42,0,255)">ALTER TABLE dumpedlines ALTER COLUMN the_geom TYPE geometry(LineString, 32631)</span><span lang="EN-US" style="font-size:10pt;font-family:Consolas"><u></u><u></u></span></p>
<p class="MsoNormal"><span style="font-size:10pt;font-family:Consolas;color:rgb(187,0,94)"><u></u> <u></u></span></p>
<p class="MsoNormal"><span lang="EN-US">Then I try to delete the lines outside the buffered polygons:<u></u><u></u></span></p>
<p class="MsoNormal"><span lang="EN-US" style="font-size:10pt;font-family:Consolas;color:rgb(42,0,255)">Delete from dumpedlines b WHERE b.pkkey NOT IN (SELECT b.pkkey FROM dumpedlines b, polygon layer c WHERE ST_within(b.the_geom, c.the_geom))<u></u><u></u></span></p>
<p class="MsoNormal"><span lang="EN-US"><u></u> <u></u></span></p>
<p class="MsoNormal"><span lang="EN-US">The result is not correct according to me, all the lines outside the buffered polygons are erased, but also SOME lines inside the buffered polygons (that are already cut by the polygons). I’ve also tried with _<i>ST</i>_within
but with the same result.<u></u><u></u></span></p>
<p class="MsoNormal"><span lang="EN-US"><u></u> <u></u></span></p>
<p class="MsoNormal"><span lang="EN-US">Any ideas?<u></u><u></u></span></p>
<p class="MsoNormal"><span lang="EN-US">Thanks in advance,<u></u><u></u></span></p>
<p class="MsoNormal"><span lang="EN-US">Paul<u></u><u></u></span></p>
</div>
</div>
_______________________________________________<br>
postgis-users mailing list<br>
<a href="mailto:postgis-users@lists.osgeo.org" target="_blank">postgis-users@lists.osgeo.org</a><br>
<a href="https://lists.osgeo.org/mailman/listinfo/postgis-users" rel="noreferrer" target="_blank">https://lists.osgeo.org/mailman/listinfo/postgis-users</a></blockquote></div></div>