[relate] fix: add missing handling of single geometries for which no IPs were generated (exterior ring inside, hole outside)

This commit is contained in:
Adam Wulkiewicz
2014-04-08 15:33:18 +02:00
parent 1c7fa89626
commit 9e00853dfa
2 changed files with 52 additions and 2 deletions

View File

@@ -93,6 +93,38 @@ public:
update<boundary, interior, '1', TransposeResult>(m_result);
update<exterior, interior, '2', TransposeResult>(m_result);
m_flags |= 1;
// TODO: OPTIMIZE!
// Only the interior rings of other ONE single geometry must be checked
// NOT all geometries
// Check if any interior ring is outside
ring_identifier ring_id(0, -1, 0);
for ( ; ring_id.ring_index < boost::numeric_cast<int>(geometry::num_interior_rings(areal)) ;
++ring_id.ring_index )
{
typename detail::sub_range_return_type<Areal const>::type
range_ref = detail::sub_range(areal, ring_id);
if ( boost::empty(range_ref) )
{
// TODO: throw exception?
continue; // ignore
}
// TODO: O(N)
// Optimize!
int pig = detail::within::point_in_geometry(range::front(range_ref), m_other_areal);
// hole outside
if ( pig < 0 )
{
update<interior, exterior, '2', TransposeResult>(m_result);
update<boundary, exterior, '1', TransposeResult>(m_result);
m_flags |= 2;
break;
}
}
}
// outside
else
@@ -101,7 +133,7 @@ public:
update<boundary, exterior, '1', TransposeResult>(m_result);
m_flags |= 2;
// If the exterior ring is outside, interior rings must be checked
// Check if any interior ring is inside
ring_identifier ring_id(0, -1, 0);
for ( ; ring_id.ring_index < boost::numeric_cast<int>(geometry::num_interior_rings(areal)) ;
++ring_id.ring_index )
@@ -126,6 +158,7 @@ public:
update<boundary, interior, '1', TransposeResult>(m_result);
update<exterior, interior, '2', TransposeResult>(m_result);
m_flags |= 1;
break;
}
}
}

View File

@@ -696,7 +696,7 @@ void polygon_polygon()
// fully containing, both with holes
test_geometry<poly, poly>("POLYGON((0 0,0 10,10 10,10 0,0 0),(3 3,7 3,7 7,3 7,3 3))",
"POLYGON((1 1,1 9,9 9,9 1,1 1),(4 4,6 4,6 6,4 6,4 4))",
"2121F12F2");
"2121F1212");
// overlapping
test_geometry<poly, poly>("POLYGON((0 0,0 10,10 10,10 0,0 0))",
@@ -826,6 +826,23 @@ void polygon_polygon()
"POLYGON((5 5,4 8,6 10,10 10,10 0,6 0,4 2,5 5))",
"212101212");
// no turns - disjoint inside a hole
test_geometry<poly, poly>("POLYGON((0 0,0 10,10 10,10 0,0 0),(1 1,9 1,9 9,1 9,1 1))",
"POLYGON((3 3,3 7,7 7,7 3,3 3))",
"FF2FF1212");
// no turns - within
test_geometry<poly, poly>("POLYGON((0 0,0 10,10 10,10 0,0 0),(1 1,9 1,9 9,1 9,1 1))",
"POLYGON((-1 -1,-1 11,11 11,11 -1,-1 -1))",
"2FF1FF212");
// no-turns - intersects
test_geometry<poly, poly>("POLYGON((0 0,0 10,10 10,10 0,0 0),(2 2,8 2,8 8,2 8,2 2))",
"POLYGON((1 1,1 9,9 9,9 1,1 1))",
"2121F12F2");
// no-turns - intersects, hole in a hole
test_geometry<poly, poly>("POLYGON((0 0,0 10,10 10,10 0,0 0),(2 2,8 2,8 8,2 8,2 2))",
"POLYGON((1 1,1 9,9 9,9 1,1 1),(3 3,7 3,7 7,3 7,3 3))",
"2121F1212");
{
test_geometry<poly, poly>("POLYGON((0 0,0 10,10 10,10 0,0 0))",
"POLYGON((5 5,5 10,6 10,6 5,5 5))",