I want to have a struct that takes an arbitrary number of lambdas and serve as a central calling point for all their call operators.
If the call operator is invoked with an argument list that doesn't match any of the lambdas given on construction, a default call operator should be called.
I thought the following code would accomplish exactly this. The call operator for every lambda is "lifted" into the Poc class via using.
template <typename ...Lambdas>
struct Poc : Lambdas...
{
using Lambdas::operator() ...; // Lift the lambda operators into the class
template <typename ...Ts>
auto operator() (Ts...)
{
std::cout << "general call" << std::endl;
}
};
// Deduction guide
template <typename ...Ts>
Poc(Ts... ts)->Poc<Ts...>;
int main()
{
auto l_int = [](int) {std::cout << "int" << std::endl; };
Poc poc{l_int};
poc(1);//calls the default operator. why?
return 0;
}
When I don't have the default call operator in the struct, everything works as expected (with valid argument lists). If I add it to the struct (as in the code above), the default operator gets called everytime, no matter which arguments I call it with.
In my understanding, the lambda-call-operators and the structs (default) call-operator are present in the same scope. Therefore, they should all be looked at for the overload resolution. Since the lamdba-operator is more specific than the generic default operator, it should be chosen.
Apparently that is not the case. Why is that?
I tested on Microsoft Visual C++, Clang and GCC (all in their latest versions).
Edit:
derivedinherits frombase<derived>. - Walter