From 47ea3400cc470521d86eac666b218e3c49d0b255 Mon Sep 17 00:00:00 2001 From: Paul Ramsey Date: Fri, 7 Jun 2013 17:39:43 +0000 Subject: [PATCH] #2351, st_distance between geographies wrong git-svn-id: http://svn.osgeo.org/postgis/trunk@11535 b70326c6-7e19-0410-871a-916f4a2858ee --- NEWS | 1 + liblwgeom/cunit/cu_geodetic.c | 17 +++++++++++++++++ liblwgeom/cunit/cu_tree.c | 19 +++++++++++++++++++ liblwgeom/lwgeodetic.c | 3 +++ 4 files changed, 40 insertions(+) diff --git a/NEWS b/NEWS index 97f8e023b..b71feba65 100644 --- a/NEWS +++ b/NEWS @@ -205,6 +205,7 @@ PostGIS 2.1.0 - #2307, ST_MakeValid outputs invalid geometries - #2309, Remove confusing INFO message when trying to get SRS info - #2348, Provide raster upgrade path for 2.0 to 2.1 + - #2351, st_distance between geographies wrong PostGIS 2.0.3 2013/03/01 diff --git a/liblwgeom/cunit/cu_geodetic.c b/liblwgeom/cunit/cu_geodetic.c index d154c061a..ab4fdbefd 100644 --- a/liblwgeom/cunit/cu_geodetic.c +++ b/liblwgeom/cunit/cu_geodetic.c @@ -702,6 +702,15 @@ static void test_edge_distance_to_point(void) CU_ASSERT_DOUBLE_EQUAL(closest.lat, 0.0, 0.00001); CU_ASSERT_DOUBLE_EQUAL(closest.lon, 0.0, 0.00001); + /* Ticket #2351 */ + edge_set(149.386990599235, -26.3567415843982, 149.386990599247, -26.3567415843965, &e); + point_set(149.386990599235, -26.3567415843982, &g); + d = edge_distance_to_point(&e, &g, &closest); + CU_ASSERT_DOUBLE_EQUAL(d, 0.0, 0.00001); + // printf("CLOSE POINT(%g %g)\n", closest.lon, closest.lat); + // printf(" ORIG POINT(%g %g)\n", g.lon, g.lat); + CU_ASSERT_DOUBLE_EQUAL(g.lat, closest.lat, 0.00001); + CU_ASSERT_DOUBLE_EQUAL(g.lon, closest.lon, 0.00001); } static void test_edge_distance_to_edge(void) @@ -1178,6 +1187,14 @@ static void test_lwgeom_distance_sphere(void) lwgeom_free(lwg1); lwgeom_free(lwg2); + /* Ticket #2351 */ + lwg1 = lwgeom_from_wkt("LINESTRING(149.386990599235 -26.3567415843982,149.386990599247 -26.3567415843965)", LW_PARSER_CHECK_NONE); + lwg2 = lwgeom_from_wkt("POINT(149.386990599235 -26.3567415843982)", LW_PARSER_CHECK_NONE); + d = lwgeom_distance_spheroid(lwg1, lwg2, &s, 0.0); + CU_ASSERT_DOUBLE_EQUAL(d, 0.0, 0.00001); + lwgeom_free(lwg1); + lwgeom_free(lwg2); + } static void test_spheroid_distance(void) diff --git a/liblwgeom/cunit/cu_tree.c b/liblwgeom/cunit/cu_tree.c index 72f9456b7..be598c2d3 100644 --- a/liblwgeom/cunit/cu_tree.c +++ b/liblwgeom/cunit/cu_tree.c @@ -264,6 +264,25 @@ static void test_tree_circ_distance(void) lwgeom_free(lwg1); lwgeom_free(lwg2); CU_ASSERT_DOUBLE_EQUAL(d1, d2, 0.00001); + + + /* Ticket #2351 */ + lwg1 = lwgeom_from_wkt("LINESTRING(149.386990599235 -26.3567415843982,149.386990599247 -26.3567415843965)", LW_PARSER_CHECK_NONE); + lwg2 = lwgeom_from_wkt("POINT(149.386990599235 -26.3567415843982)", LW_PARSER_CHECK_NONE); + c1 = lwgeom_calculate_circ_tree(lwg1); + c2 = lwgeom_calculate_circ_tree(lwg2); + d1 = circ_tree_distance_tree(c1, c2, &s, threshold); + d2 = lwgeom_distance_spheroid(lwg1, lwg2, &s, threshold); + // printf("d1 = %g d2 = %g\n", d1 * WGS84_RADIUS, d2 * WGS84_RADIUS); + // printf("line\n"); + // circ_tree_print(c1, 0); + // printf("point\n"); + // circ_tree_print(c2, 0); + circ_tree_free(c1); + circ_tree_free(c2); + lwgeom_free(lwg1); + lwgeom_free(lwg2); + CU_ASSERT_DOUBLE_EQUAL(d1, d2, 0.0000001); } diff --git a/liblwgeom/lwgeodetic.c b/liblwgeom/lwgeodetic.c index dcbabeca7..a542a870e 100644 --- a/liblwgeom/lwgeodetic.c +++ b/liblwgeom/lwgeodetic.c @@ -1170,7 +1170,10 @@ double edge_distance_to_point(const GEOGRAPHIC_EDGE *e, const GEOGRAPHIC_POINT * /* Zero length edge, */ if ( geographic_point_equals(&(e->start), &(e->end)) ) + { + *closest = e->start; return sphere_distance(&(e->start), gp); + } robust_cross_product(&(e->start), &(e->end), &n); normalize(&n); -- 2.50.1