From 32bffa6a642e60ca647518b19489c2e3145efe42 Mon Sep 17 00:00:00 2001 From: David Brochart Date: Sat, 8 Jun 2019 10:39:41 +0200 Subject: [PATCH 1/3] WIP --- include/xframe/xaxis.hpp | 20 ++++++++++++++++++++ include/xframe/xvariable.hpp | 2 ++ include/xframe/xvariable_view.hpp | 5 +++-- 3 files changed, 25 insertions(+), 2 deletions(-) diff --git a/include/xframe/xaxis.hpp b/include/xframe/xaxis.hpp index 2698189..ec25cd6 100644 --- a/include/xframe/xaxis.hpp +++ b/include/xframe/xaxis.hpp @@ -9,6 +9,8 @@ #ifndef XFRAME_XAXIS_HPP #define XFRAME_XAXIS_HPP +extern double global_tolerance; + #include #include #include @@ -412,6 +414,24 @@ namespace xf template inline auto xaxis::operator[](const key_type& key) const -> mapped_type { + if constexpr (std::is_floating_point::value) + { + if (global_tolerance > 0.) + { + double smallest; + int position = -1; + for (const auto& it: m_index) + { + double diff = fabs(double(it.first) - key); + if ((diff <= global_tolerance) && ((position < 0) || (diff < smallest))) + { + smallest = diff; + position = it.second; + } + } + return position >= 0 ? position : m_index.at(key); + } + } return m_index.at(key); } //@} diff --git a/include/xframe/xvariable.hpp b/include/xframe/xvariable.hpp index ccf3d20..c2a4a8b 100644 --- a/include/xframe/xvariable.hpp +++ b/include/xframe/xvariable.hpp @@ -15,6 +15,8 @@ #include "xvariable_base.hpp" #include "xvariable_math.hpp" +double global_tolerance = 0.; + namespace xf { /*********************** diff --git a/include/xframe/xvariable_view.hpp b/include/xframe/xvariable_view.hpp index 364f0fc..fa4af02 100644 --- a/include/xframe/xvariable_view.hpp +++ b/include/xframe/xvariable_view.hpp @@ -281,7 +281,7 @@ namespace xf auto locate(E&& e, S&&... slices); template - auto select(E&& e, std::map::key_type, xaxis_slice>&& slices); + auto select(E&& e, std::map::key_type, xaxis_slice>&& slices, double tolerance=0.); template ::difference_type> auto iselect(E&& e, std::map::key_type, xt::xdynamic_slice>&& slices); @@ -1089,8 +1089,9 @@ namespace xf } template - inline auto select(E&& e, std::map::key_type, xaxis_slice>&& slices) + inline auto select(E&& e, std::map::key_type, xaxis_slice>&& slices, double tolerance) { + global_tolerance = tolerance; using coordinate_type = typename std::decay_t::coordinate_type; using dimension_type = typename std::decay_t::dimension_type; using dimension_label_list = typename dimension_type::label_list; From e7e94e2655456e108bd149bb463de552402bf842 Mon Sep 17 00:00:00 2001 From: David Brochart Date: Sat, 8 Jun 2019 12:28:10 +0200 Subject: [PATCH 2/3] C++14 compatible --- include/xframe/xaxis.hpp | 61 ++++++++++++++++++++++++++++------------ 1 file changed, 43 insertions(+), 18 deletions(-) diff --git a/include/xframe/xaxis.hpp b/include/xframe/xaxis.hpp index ec25cd6..79a3811 100644 --- a/include/xframe/xaxis.hpp +++ b/include/xframe/xaxis.hpp @@ -116,6 +116,10 @@ namespace xf bool contains(const key_type& key) const; mapped_type operator[](const key_type& key) const; + mapped_type tolerance(const key_type& key, std::true_type) const; + mapped_type tolerance(const key_type& key, std::false_type) const; + mapped_type with_tolerance(const key_type& key) const; + mapped_type without_tolerance(const key_type& key) const; template self_type filter(const F& f) const noexcept; @@ -406,34 +410,55 @@ namespace xf return m_index.count(key) != typename map_type::size_type(0); } - /** - * Returns the position of the specified label. If this last one is - * not found, an exception is thrown. - * @param key the label to search for. - */ template - inline auto xaxis::operator[](const key_type& key) const -> mapped_type + inline auto xaxis::tolerance(const key_type& key, std::true_type) const -> mapped_type + { + return with_tolerance(key); + } + + template + inline auto xaxis::tolerance(const key_type& key, std::false_type) const -> mapped_type + { + return without_tolerance(key); + } + + template + inline auto xaxis::with_tolerance(const key_type& key) const -> mapped_type { - if constexpr (std::is_floating_point::value) + if (global_tolerance > 0.) { - if (global_tolerance > 0.) + double smallest; + int position = -1; + for (const auto& it: m_index) { - double smallest; - int position = -1; - for (const auto& it: m_index) + double diff = fabs(double(it.first) - key); + if ((diff <= global_tolerance) && ((position < 0) || (diff < smallest))) { - double diff = fabs(double(it.first) - key); - if ((diff <= global_tolerance) && ((position < 0) || (diff < smallest))) - { - smallest = diff; - position = it.second; - } + smallest = diff; + position = it.second; } - return position >= 0 ? position : m_index.at(key); } + return position >= 0 ? position : m_index.at(key); } return m_index.at(key); } + + template + inline auto xaxis::without_tolerance(const key_type& key) const -> mapped_type + { + return m_index.at(key); + } + + /** + * Returns the position of the specified label. If this last one is + * not found, an exception is thrown. + * @param key the label to search for. + */ + template + inline auto xaxis::operator[](const key_type& key) const -> mapped_type + { + return tolerance(key, std::integral_constant::value>{}); + } //@} /** From 37077cf5b07d09a9624533dae7a2cf4642b266fb Mon Sep 17 00:00:00 2001 From: David Brochart Date: Sat, 8 Jun 2019 12:40:44 +0200 Subject: [PATCH 3/3] Move global_tolerance to main() --- include/xframe/xvariable.hpp | 2 -- 1 file changed, 2 deletions(-) diff --git a/include/xframe/xvariable.hpp b/include/xframe/xvariable.hpp index c2a4a8b..ccf3d20 100644 --- a/include/xframe/xvariable.hpp +++ b/include/xframe/xvariable.hpp @@ -15,8 +15,6 @@ #include "xvariable_base.hpp" #include "xvariable_math.hpp" -double global_tolerance = 0.; - namespace xf { /***********************