В обеих функциях мы выполняем итерацию в диапазоне от начала std::set
до заданного итератора, который зависит от входного значения.
В этом ответе я предполагаю, что compBLess
и compBGreater
определены следующим образом (важная часть заключается в том, что поле b1 преобладает над b2. И посмотрите в конце несколько отличную версию)
struct compBLess {
bool operator ()(B const & o1, B const& o2) const {
return std::make_pair(o1.b1,o1.b2) < std::make_pair(o2.b1,o2.b2);
}
};
struct compBGreater {
bool operator ()(B const & o1, B const& o2) const {
return std::make_pair(o1.b1,o1.b2) > std::make_pair(o2.b1,o2.b2);
}
};
В этом предположении, я думаю, что идиоматический способ сделать это состоит в том, чтобы использовать нижний, верхний методы std :: set , чтобы найти конец итерации, а затем использовать
template<typename Iterator>
void foo(Iterator it, Iterator end) {
std::for_each(it,end,[this](auto & o){ sameForBoth(o); });
}
Это будет более эффективным с точки зрения производительности, потому что мы будем делать O (log (size_of_set)) сравнений (используя нижний / верхний) вместо O (size_of_set) сравнений (используя comp
в цикле)
Фактическая реализация других методов выглядит следующим образом:
void onFirst(int val) {
foo(m_setLess.begin(), m_setLess.lowerbound({val,std::numeric_limits<int>::min}));
}
void onSecond(int val) {
foo(m_setGreater.begin(), m_setGreater.upperbound({val-1,std::numeric_limits<int>::max}));
}
Редактировать: После комментария @ z3dd, вот реализация, которая работает для слегка отличающихся compBLess
и compBGreater
(упорядочение по сравнению с полем b2
обращено):
struct compBLess {
bool operator ()(B const & o1, B const& o2) const {
return std::make_pair(o1.b1,-o1.b2) < std::make_pair(o2.b1,-o2.b2);
}
};
struct compBGreater {
bool operator ()(B const & o1, B const& o2) const {
return std::make_pair(o1.b1,-o1.b2) > std::make_pair(o2.b1,-o2.b2);
}
};
void onFirst(int val) {
foo(m_setLess.begin(), m_setLess.lowerbound({val,std::numeric_limits<int>::max}));
}
void onSecond(int val) {
foo(m_setGreater.begin(), m_setGreater.upperbound({val-1,std::numeric_limits<int>::min}));
}
[Обратите внимание, что если compBLess
и compBGreater
не реализованы так, как любая из двух приведенных реализаций, то ответ @Ilio Catallo - тот, который нужно использовать.]