I have a class with some static functions. The class constructor takes a function as one of its arguments.
template <typename T>
class MyClass {
public:
static std::function<T(T, T)> func1 = [](T a, T b) {
...
}
static std::function<T(T, T)> func2 = [](T a, T b) {
...
}
MyClass(std::function<T(T, T)> func) {
...
}
}
When I initialize an object from this class:
MyClass<int> myObj(MyClass.func1);
The compiler complains that:
> argument list for class template "MyClass" is missing.
What is the correct way to do this while keeping the functions in the class itself?
CodePudding user response:
MyClass
is a template not a class. The class that has a static member you want to pass to the constructor is MyClass<int>
.
Your code has some typos (missing ;
), I had to add inline
for in-class initialization of the static members, I introduced an alias, and for brevity I used struct
rather than class
(the class has only public members):
#include <iostream>
#include <functional>
template <typename T>
struct MyClass {
using fun_t = std::function<T(T,T)>;
static inline fun_t func1 = [](T a, T b) { return a b; };
static inline fun_t func2 = [](T a, T b) { return a-b; };
fun_t fun;
MyClass(std::function<T(T, T)> func) : fun(func) {}
};
int main() {
auto x = MyClass<int>{MyClass<int>::func1};
std::cout << x.fun(1,2);
}
As pointed out in comments by AyxanHaqverdili, this would work as well:
auto x = MyClass{ MyClass<int>::func1 };
due to CTAD (class template argument deduction) where the class templates argument is deduced from the constructors parameters. Live Demo
Also this is fine, although a bit hacky, and I don't recommend to actually use it:
MyClass<int> x { x.func1 };
In a nutshell: You can refer to a variable in its own initializer. We aren't doing something that would require x
to be fully initialized, so there is no problem with accessing the (already initialized) static
member via an instance of MyClass<int>
. Live Demo
A less suspicious variant of this suggested by @HTNW is
MyClass<int> x{decltype(x)::func1};
Now it is more obvious that we only use the type of x
and access a static member of its class.