use integer approximation for polyline generalization
This commit is contained in:
parent
21eb5b661d
commit
f3ad14cb7f
@ -38,25 +38,25 @@ SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
||||
#include <limits>
|
||||
|
||||
DouglasPeucker::DouglasPeucker()
|
||||
: douglas_peucker_thresholds({262144.f, // z0
|
||||
131072.f, // z1
|
||||
65536.f, // z2
|
||||
32768.f, // z3
|
||||
16384.f, // z4
|
||||
8192.f, // z5
|
||||
4096.f, // z6
|
||||
2048.f, // z7
|
||||
960.f, // z8
|
||||
480.f, // z9
|
||||
240.f, // z10
|
||||
90.f, // z11
|
||||
50.f, // z12
|
||||
25.f, // z13
|
||||
15.f, // z14
|
||||
5.f, // z15
|
||||
.65f, // z16
|
||||
.5f, // z17
|
||||
.35f // z18
|
||||
: douglas_peucker_thresholds({2621440, // z0
|
||||
1310720, // z1
|
||||
655360, // z2
|
||||
327680, // z3
|
||||
163840, // z4
|
||||
81920, // z5
|
||||
40960, // z6
|
||||
20480, // z7
|
||||
9600, // z8
|
||||
4800, // z9
|
||||
2800, // z10
|
||||
900, // z11
|
||||
600, // z12
|
||||
275, // z13
|
||||
160, // z14
|
||||
60, // z15
|
||||
8, // z16
|
||||
6, // z17
|
||||
4 // z18
|
||||
})
|
||||
{
|
||||
}
|
||||
@ -79,16 +79,10 @@ void DouglasPeucker::Run(std::vector<SegmentInformation> &input_geometry, const
|
||||
// Sweep over array and identify those ranges that need to be checked
|
||||
do
|
||||
{
|
||||
if (!input_geometry[left_border].necessary)
|
||||
{
|
||||
SimpleLogger().Write() << "broken interval [" << left_border << "," << right_border << "]";
|
||||
}
|
||||
BOOST_ASSERT_MSG(input_geometry[left_border].necessary,
|
||||
"left border must be necessary");
|
||||
BOOST_ASSERT_MSG(input_geometry.back().necessary, "right border must be necessary");
|
||||
|
||||
if (input_geometry[right_border].necessary)
|
||||
{
|
||||
BOOST_ASSERT(input_geometry[left_border].necessary);
|
||||
BOOST_ASSERT(input_geometry[right_border].necessary);
|
||||
recursion_stack.emplace(left_border, right_border);
|
||||
left_border = right_border;
|
||||
}
|
||||
@ -104,24 +98,24 @@ void DouglasPeucker::Run(std::vector<SegmentInformation> &input_geometry, const
|
||||
BOOST_ASSERT_MSG(input_geometry[pair.second].necessary, "right border must be necessary");
|
||||
BOOST_ASSERT_MSG(pair.second < input_geometry.size(), "right border outside of geometry");
|
||||
BOOST_ASSERT_MSG(pair.first < pair.second, "left border on the wrong side");
|
||||
float max_distance = std::numeric_limits<float>::min();
|
||||
int max_int_distance = 0;
|
||||
|
||||
unsigned farthest_element_index = pair.second;
|
||||
// find index idx of element with max_distance
|
||||
for (unsigned i = pair.first + 1; i < pair.second; ++i)
|
||||
{
|
||||
const float temp_dist = FixedPointCoordinate::ComputePerpendicularDistance(
|
||||
const int int_dist = FixedPointCoordinate::OrderedPerpendicularDistanceApproximation(
|
||||
input_geometry[i].location,
|
||||
input_geometry[pair.first].location,
|
||||
input_geometry[pair.second].location);
|
||||
const float distance = std::abs(temp_dist);
|
||||
if (distance > douglas_peucker_thresholds[zoom_level] && distance > max_distance)
|
||||
|
||||
if (int_dist > max_int_distance && int_dist > douglas_peucker_thresholds[zoom_level])
|
||||
{
|
||||
farthest_element_index = i;
|
||||
max_distance = distance;
|
||||
max_int_distance = int_dist;
|
||||
}
|
||||
}
|
||||
if (max_distance > douglas_peucker_thresholds[zoom_level])
|
||||
if (max_int_distance > douglas_peucker_thresholds[zoom_level])
|
||||
{
|
||||
// mark idx as necessary
|
||||
input_geometry[farthest_element_index].necessary = true;
|
||||
|
@ -44,7 +44,7 @@ struct SegmentInformation;
|
||||
class DouglasPeucker
|
||||
{
|
||||
private:
|
||||
std::vector<float> douglas_peucker_thresholds;
|
||||
std::vector<int> douglas_peucker_thresholds;
|
||||
|
||||
typedef std::pair<unsigned, unsigned> GeometryRange;
|
||||
// Stack to simulate the recursion
|
||||
|
Loading…
Reference in New Issue
Block a user