How would I go about storing any type of function with any number of arguments in a variable? Something like this:
int add(int i, int j) {
return i + j;
}
template<typename Function, typename... Args>
class Class {
private:
std::function<Function(Args...)> function;
public:
Class(Function _function, Args... _args) {
Now what?
}
};
int main() {
Class test(add, 1, 2);
test.function();
}
This is what bind
is for!
Your Class
is effectively just std::bind
. Let's imagine that you have further use for it, and make it wrap the std::bind
logic. So we need to store a std::function
that accepts no further arguments, and returns (in this case) int
… but we'll make it generic (ReturnType
).
Then during initialisation you "bind" the arguments with which you constructed Class
, and forward them into the std::function
(the use of std::forward
permitting move semantics for more complex argument types).
#include <functional>
#include <iostream>
int add(int i, int j)
{
return i + j;
}
template <typename Function, typename... Args>
class Class
{
private:
using ReturnType = std::invoke_result_t<Function, Args...>;
std::function<ReturnType()> function;
public:
Class(Function _function, Args... _args)
: function(std::bind(_function, std::forward<Args>(_args)...))
{}
auto Call()
{
return function();
}
};
int main() {
Class test(add, 1, 2);
std::cout << test.Call() << '\n';
}
// Output: 3
Or, if you don't need Class
to do anything more, it's just:
#include <functional>
#include <iostream>
int add(int i, int j)
{
return i + j;
}
int main()
{
auto func = std::bind(add, 1, 2);
std::cout << func() << '\n';
}
// Output: 3
Your std::function<Function(Args...)>
type is wrong because Function
is the type of the whole function, but you've used it like a return type.