[geos-devel] [GEOS] #758: LineStringSnapper snaps in wrong order in last segment of closed linestring
GEOS
geos-trac at osgeo.org
Mon Dec 14 05:54:16 PST 2015
#758: LineStringSnapper snaps in wrong order in last segment of closed linestring
------------------------+-------------------------------
Reporter: maxbo | Owner: geos-devel@…
Type: defect | Status: new
Priority: minor | Milestone: 3.5.1
Component: Default | Version: 3.5.0
Severity: Unassigned | Keywords: LineStringSnapper
------------------------+-------------------------------
st_snap(linestring, geometry) behaves not always as expected for closed
linestrings in the last segment. This seems to be a bug in the geos
LineStringSnapper class:
(using
(POSTGIS="2.1.5 r13152" GEOS="3.4.2-CAPI-1.8.2 r3924" PROJ="Rel. 4.8.0, 6
March 2012" GDAL="GDAL 1.11.1, released 2014/09/24 GDAL_DATA not found"
LIBXML="2.7.8" LIBJSON="UNKNOWN" TOPOLOGY RASTER)
The following example should demonstrate the problem:
SELECT (du).path[1] as vertex_nr, st_astext((du).geom) FROM (
SELECT st_dumppoints(st_snap(a, b, 2)) AS du FROM
(SELECT 'LINESTRING (1 1, 5 9, 9 1, 1 1)'::geometry AS a,
'MULTIPOINT(0 0, 10 0, 1 0.5)'::geometry AS b ) c
)d;
I expected that POINT(1 0.5) would be inserted into the last segment of
the LINESTRING at position 4. This point is acutally inserted, but at a
wrong position (Position 3), resulting in an "ugly" geometry.
1;POINT(0 0)
2;POINT(5 9)
3;POINT(1 0.5)
4;POINT(10 0)
5;POINT(0 0)
This behaviour only occures for a closed linestring.
Opening the linestring
SELECT (du).path[1] as vertex_nr, st_astext((du).geom) FROM (
SELECT st_dumppoints(st_snap(a, b, 2)) AS du FROM
(SELECT 'LINESTRING (0.9 0.9, 5 9, 9 1, 1 1)'::geometry AS a,
'MULTIPOINT(0 0, 10 0, 1 0.5)'::geometry AS b ) c
)d;
will take POINT(1, .5) as endpoint.
1;POINT(0 0)
2;POINT(5 9)
3;POINT(10 0)
4;POINT(1 0.5)
Shifting the start- and endpoint of the linestring
SELECT (du).path[1] as vertex_nr, st_astext((du).geom) FROM (
SELECT st_dumppoints(st_snap(a, b, 2)) AS du FROM
(SELECT 'LINESTRING (5 9, 9 1, 1 1, 5 9)'::geometry AS a,
'MULTIPOINT(0 0, 10 0, 1 0.5)'::geometry AS b ) c
)d;
results in a correct geometry, where POINT(1, .5) is inserted at position
3 between POINT(10 0) and POINT(0 0)
1;POINT(5 9)
2;POINT(10 0)
3;POINT(1 0.5)
4;POINT(0 0)
5;POINT(5 9)
Here a test for GEOSSnapTest.cpp
/// Test snapping of last segment of closed ring to snap points
{
geom1_ = GEOSGeomFromWKT("LINESTRING (1 1, 5 9, 9 1, 1 1)");
geom2_ = GEOSGeomFromWKT("MULTIPOINT(0 0, 10 0, 1 0.5)");
geom3_ = GEOSSnap(geom1_, geom2_, 2);
char* wkt_c = GEOSWKTWriter_write(w_, geom3_);
std::string out(wkt_c);
free(wkt_c);
ensure_equals(out, "LINESTRING (0 0, 5 9, 10 0, 1 0.5, 0 0)");
}
Thanks,
Max
--
Ticket URL: <https://trac.osgeo.org/geos/ticket/758>
GEOS <http://trac.osgeo.org/geos>
GEOS (Geometry Engine - Open Source) is a C++ port of the Java Topology Suite (JTS).
More information about the geos-devel
mailing list