From 45185c9501727d0001daa2c7ee56a45d096bb8cf Mon Sep 17 00:00:00 2001 From: James Gill Date: Tue, 1 Sep 2020 12:28:14 -0400 Subject: [PATCH] Fix incorrect intersection between two envelopes When two envelopes intersected at a single point, the intersection would be incorrectly calculated as `POINT(x, x)` instead of `POINT(x, y)`. This also simplifies the logic when two envelopes intersect in a line. --- .../presto/plugin/geospatial/GeoFunctions.java | 12 ++++-------- .../presto/plugin/geospatial/TestGeoFunctions.java | 1 + 2 files changed, 5 insertions(+), 8 deletions(-) diff --git a/presto-geospatial/src/main/java/com/facebook/presto/plugin/geospatial/GeoFunctions.java b/presto-geospatial/src/main/java/com/facebook/presto/plugin/geospatial/GeoFunctions.java index 6132a135fc68b..27b0079a25cc3 100644 --- a/presto-geospatial/src/main/java/com/facebook/presto/plugin/geospatial/GeoFunctions.java +++ b/presto-geospatial/src/main/java/com/facebook/presto/plugin/geospatial/GeoFunctions.java @@ -1001,15 +1001,11 @@ public static Slice stIntersection(@SqlType(GEOMETRY_TYPE_NAME) Slice left, @Sql } Envelope intersection = leftEnvelope; - if (intersection.getXMin() == intersection.getXMax()) { - if (intersection.getYMin() == intersection.getYMax()) { - return EsriGeometrySerde.serialize(createFromEsriGeometry(new Point(intersection.getXMin(), intersection.getXMax()), null)); + if (intersection.getXMin() == intersection.getXMax() || intersection.getYMin() == intersection.getYMax()) { + if (intersection.getXMin() == intersection.getXMax() && intersection.getYMin() == intersection.getYMax()) { + return EsriGeometrySerde.serialize(createFromEsriGeometry(new Point(intersection.getXMin(), intersection.getYMin()), null)); } - return EsriGeometrySerde.serialize(createFromEsriGeometry(new Polyline(new Point(intersection.getXMin(), intersection.getYMin()), new Point(intersection.getXMin(), intersection.getYMax())), null)); - } - - if (intersection.getYMin() == intersection.getYMax()) { - return EsriGeometrySerde.serialize(createFromEsriGeometry(new Polyline(new Point(intersection.getXMin(), intersection.getYMin()), new Point(intersection.getXMax(), intersection.getYMin())), null)); + return EsriGeometrySerde.serialize(createFromEsriGeometry(new Polyline(new Point(intersection.getXMin(), intersection.getYMin()), new Point(intersection.getXMax(), intersection.getYMax())), null)); } return EsriGeometrySerde.serialize(intersection); diff --git a/presto-geospatial/src/test/java/com/facebook/presto/plugin/geospatial/TestGeoFunctions.java b/presto-geospatial/src/test/java/com/facebook/presto/plugin/geospatial/TestGeoFunctions.java index c7ed7921efdea..e829f5fb3fee8 100644 --- a/presto-geospatial/src/test/java/com/facebook/presto/plugin/geospatial/TestGeoFunctions.java +++ b/presto-geospatial/src/test/java/com/facebook/presto/plugin/geospatial/TestGeoFunctions.java @@ -857,6 +857,7 @@ public void testSTIntersection() assertEnvelopeIntersection("POLYGON ((0 0, 0 5, 5 5, 5 0, 0 0))", "POLYGON ((-1 -1, 0 -1, 0 1, -1 1, -1 -1))", "LINESTRING (0 0, 0 1)"); assertEnvelopeIntersection("POLYGON ((0 0, 0 5, 5 5, 5 0, 0 0))", "POLYGON ((1 -1, 2 -1, 2 0, 1 0, 1 -1))", "LINESTRING (1 0, 2 0)"); assertEnvelopeIntersection("POLYGON ((0 0, 0 5, 5 5, 5 0, 0 0))", "POLYGON ((-1 -1, 0 -1, 0 0, -1 0, -1 -1))", "POINT (0 0)"); + assertEnvelopeIntersection("POLYGON ((0 0, 0 5, 5 5, 5 0, 0 0))", "POLYGON ((5 -1, 5 0, 6 0, 6 -1, 5 -1))", "POINT (5 0)"); } private void assertEnvelopeIntersection(String envelope, String otherEnvelope, String intersection)