Welcome to mirror list, hosted at ThFree Co, Russian Federation.

github.com/mapsme/omim.git - Unnamed repository; edit this file 'description' to name the repository.
summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorvng <viktor.govako@gmail.com>2011-01-25 21:57:27 +0300
committerAlex Zolotarev <alex@maps.me>2015-09-23 01:10:52 +0300
commitab660b4f6857cf8ff57da65d4d33a3cc9b8876db (patch)
treec91eacb263c35bcb0b6a1e0cdfddaad713941bfd /geometry/geometry_tests/region_test.cpp
parent9520a1cd23565d785a645742841b5a8aa869c7d6 (diff)
Region with good calculation-overflow processing.
Better Region::Contains code.
Diffstat (limited to 'geometry/geometry_tests/region_test.cpp')
-rw-r--r--geometry/geometry_tests/region_test.cpp106
1 files changed, 76 insertions, 30 deletions
diff --git a/geometry/geometry_tests/region_test.cpp b/geometry/geometry_tests/region_test.cpp
index da6d7d9b36..afaf24498b 100644
--- a/geometry/geometry_tests/region_test.cpp
+++ b/geometry/geometry_tests/region_test.cpp
@@ -4,20 +4,63 @@
#include "../region2d.hpp"
-template<class RegionT> struct ContainsChecker
+
+namespace {
+
+template <class RegionT> struct ContainsChecker
{
- RegionT & m_region;
- ContainsChecker(RegionT & region) : m_region(region) {}
+ RegionT const & m_region;
+ ContainsChecker(RegionT const & region) : m_region(region) {}
void operator()(typename RegionT::value_type const & pt)
{
TEST(m_region.Contains(pt), ("Region should contain all it's points"));
}
};
-template<class RegionT>
-void Test()
+/// Region should have CCW orientation from left, down corner.
+template <class PointT>
+void TestContainsRectangular(PointT const * arr)
+{
+ m2::Region<PointT> region;
+
+ size_t const count = 4;
+ region.Assign(arr, arr + count);
+
+ for (size_t i = 0; i < count; ++i)
+ {
+ region.Contains(arr[i]);
+ region.Contains((arr[i] + arr[(i + count - 1) % count]) / 2);
+ }
+
+ PointT dx(1, 0);
+ PointT dy(0, 1);
+
+ TEST(!region.Contains(arr[0] - dx), ());
+ TEST(!region.Contains(arr[0] - dy), ());
+ TEST(!region.Contains(arr[0] - dx - dy), ());
+ TEST(region.Contains(arr[0] + dx + dy), ());
+
+ TEST(!region.Contains(arr[1] + dx), ());
+ TEST(!region.Contains(arr[1] - dy), ());
+ TEST(!region.Contains(arr[1] + dx - dy), ());
+ TEST(region.Contains(arr[1] - dx + dy), ());
+
+ TEST(!region.Contains(arr[2] + dx), ());
+ TEST(!region.Contains(arr[2] + dy), ());
+ TEST(!region.Contains(arr[2] + dx + dy), ());
+ TEST(region.Contains(arr[2] - dx - dy), ());
+
+ TEST(!region.Contains(arr[3] - dx), ());
+ TEST(!region.Contains(arr[3] + dy), ());
+ TEST(!region.Contains(arr[3] - dx + dy), ());
+ TEST(region.Contains(arr[3] + dx - dy), ());
+}
+
+template <class RegionT>
+void TestContaints()
{
RegionT region;
+ ContainsChecker<RegionT> checker(region);
// point type
typedef typename RegionT::value_type P;
@@ -25,18 +68,22 @@ void Test()
// rectangular polygon
{
P const data[] = { P(1, 1), P(10, 1), P(10, 10), P(1, 10) };
- region.Assign(data, data + ARRAY_SIZE(data));
+ TestContainsRectangular(data);
+ }
+ {
+ P const data[] = { P(-100, -100), P(-50, -100), P(-50, -50), P(-100, -50) };
+ TestContainsRectangular(data);
+ }
+ {
+ P const data[] = { P(-2000000000, -2000000000), P(-1000000000, -2000000000),
+ P(-1000000000, -1000000000), P(-2000000000, -1000000000) };
+ TestContainsRectangular(data);
+ }
+ {
+ P const data[] = { P(1000000000, 1000000000), P(2000000000, 1000000000),
+ P(2000000000, 2000000000), P(1000000000, 2000000000) };
+ TestContainsRectangular(data);
}
- TEST_EQUAL(region.Rect(), m2::Rect<typename P::value_type>(1, 1, 10, 10), ());
-
- TEST(region.Contains(P(1, 1)), ());
- TEST(region.Contains(P(2, 2)), ());
- TEST(region.Contains(P(10, 5)), ());
- TEST(region.Contains(P(1, 6)), ());
- TEST(!region.Contains(P(0, 0)), ());
- TEST(!region.Contains(P(100, 0)), ());
- ContainsChecker<RegionT> checker(region);
- region.ForEachPoint(checker);
// triangle
{
@@ -68,6 +115,8 @@ void Test()
region.ForEachPoint(checker);
}
+}
+
UNIT_TEST(Region)
{
typedef m2::PointD P;
@@ -89,9 +138,9 @@ UNIT_TEST(Region)
UNIT_TEST(Region_Contains)
{
- Test<m2::RegionD>();
- Test<m2::RegionF>();
- Test<m2::RegionI>();
+ TestContaints<m2::RegionU>();
+ TestContaints<m2::RegionD>();
+ TestContaints<m2::RegionI>();
// negative triangle
{
@@ -122,16 +171,14 @@ UNIT_TEST(Region_Contains)
}
}
-template <class TPoint>
-struct PointsSummator
+template <class TPoint> class PointsSummator
{
- double m_xSumm;
- double m_ySumm;
- PointsSummator() : m_xSumm(0), m_ySumm(0) {}
+ TPoint & m_res;
+public:
+ PointsSummator(TPoint & res) : m_res(res) {}
void operator()(TPoint const & pt)
{
- m_xSumm += pt.x;
- m_ySumm += pt.y;
+ m_res += pt;
}
};
@@ -141,9 +188,8 @@ UNIT_TEST(Region_ForEachPoint)
P const points[] = { P(0.0, 1.0), P(1.0, 2.0), P(10.5, 11.5) };
m2::Region<P> region(points, points + ARRAY_SIZE(points));
- PointsSummator<P> s;
- region.ForEachPoint(s);
+ P res(0, 0);
+ region.ForEachPoint(PointsSummator<P>(res));
- TEST_EQUAL(s.m_xSumm, 11.5, ());
- TEST_EQUAL(s.m_ySumm, 14.5, ());
+ TEST_EQUAL(res, P(11.5, 14.5), ());
}