Skip to content

Commit

Permalink
Refs #11659. Replace recursive binary search with std::lower_bound
Browse files Browse the repository at this point in the history
  • Loading branch information
Michael Wedel committed Apr 30, 2015
1 parent 2b203e0 commit 565fda0
Showing 1 changed file with 18 additions and 11 deletions.
29 changes: 18 additions & 11 deletions Code/Mantid/Framework/Kernel/src/Interpolation.cpp
Expand Up @@ -10,6 +10,15 @@ namespace {
Logger g_log("Interpolation");
}

/* Functor for findIndexOfNextLargerValue, used in std::lower_bound to replicate
the original behavior.
*/
struct LessOrEqualFunctor {
bool operator()(const double &lhs, const double &rhs) {
return lhs <= rhs;
}
};

/** Constructor default to linear interpolation and x-unit set to TOF
*/
Interpolation::Interpolation() : m_method("linear") {
Expand All @@ -21,21 +30,19 @@ size_t
Interpolation::findIndexOfNextLargerValue(const std::vector<double> &data,
double key, size_t range_start,
size_t range_end) const {
if (range_end < range_start) {
throw std::range_error("Value is outside array range.");
}

size_t center = range_start + (range_end - range_start) / 2;
UNUSED_ARG(range_start);
UNUSED_ARG(range_end);

if (data[center] > key && data[center - 1] <= key) {
return center;
}
auto begin = data.begin();
auto end = data.end();
auto pos = std::lower_bound(begin, end, key, LessOrEqualFunctor());

if (data[center] <= key) {
return findIndexOfNextLargerValue(data, key, center + 1, range_end);
} else {
return findIndexOfNextLargerValue(data, key, range_start, center - 1);
if(pos == end || pos == begin) {
throw std::range_error("Value is not in the interpolation range.");
}

return std::distance(begin, pos);
}

void Interpolation::setXUnit(const std::string &unit) {
Expand Down

0 comments on commit 565fda0

Please sign in to comment.