Reputation: 11
I want to implement the following for more than one (i.e. many) functions (function1(), function2(), ...etc.).
Currently I have it separately as follows:
template <typename T>
concept iterator_1 = requires(T const& t) {
t.function1();
};
template <iterator_1 R>
static float getterFunction(R const& r)
{
return r.function1();
}
template <typename T>
concept iterator_2 = requires(T const& t) {
t.function2();
};
template <iterator_2 R>
static float getterFunction(R const& r)
{
return r.function2();
}
I want to use a general getterFunction to choose function1(), function2(), ...etc. with an if condition, such as follows:
template <typename A>
float getterFunction(A const& a)
{
auto i = -1;
if (something==0) {
i = a.function1();
}
else if (something==1) {
i = a.function2();
}
else if {
...
}
return i;
}
I would like to use this general getterFunction as follows:
template <typename B>
void DoSomething(typename B::iterator const& b)
{
float value = getterFunction(b);
...
}
I was wondering if there is a more general way of doing this, instead of writing many concepts for each of the many functions?
Upvotes: 1
Views: 47
Reputation: 545
Since concepts are checked at compile time, you could use if constexpr
which discards any non-taken branch:
template <typename A>
auto getterFunction(A const& a)
{
if constexpr (iterator_1<A>) {
return a.function1();
} else if constexpr (iterator_2<A>) {
return a.function2();
} else {
static_assert(false);
}
}
}
You may want to consider adding a check that only one concept is satisfied, as any type which satisfies more will just use the first one in the checked order. static_assert(std::ranges::count({ iterator_1<A>, iterator_2<A>... }, true) == 1);
should do the trick.
Upvotes: 1