Reputation: 111
Okay, so I'm writing a simple GUI framework. I stumbled across lambda expressions and thought they'd be a good way to do callbacks. But I can't figure out how to retain the expression in class (very simplified example code below).
class class1
{
public:
class1(auto callback);
private:
const auto mCallback
};
class1::class1(auto callback) : mCallback(callback)
{
}
int main()
{
auto thiscode = [] (int id)
{
std::cout<<"callback from..." << id << std::endl;
};
class1 c1 = class1(thiscode);
}
I end up with this error,
error: non-static data member declared 'auto'
Which I suppose makes sense, it can't determine the size at run time. In fact, below C++14 it won't even allow me to pass auto callback
as a paramter to the constructor. (I think that changed in a readying process for concepts?).
How do I get around this? I don't mind having to do something weird, anything that allows me to retain a reference to the passed lambda expression - I'm golden with.
Upvotes: 2
Views: 144
Reputation: 11032
You can use std::function to store thiscode
.
Something like this:
#include <functional>
#include <iostream>
class class1 {
public:
class1(std::function<void(int)> callback) : mCallback{callback} {};
void do_callback() { mCallback(3); };
private:
const std::function<void(int)> mCallback;
};
int main()
{
auto thiscode = [](int id) {
std::cout<<"callback from..." << id << std::endl;
};
class1 c1 = class1(thiscode);
c1.do_callback();
return 0;
}
See live demo here.
Upvotes: 4
Reputation: 41840
You can hold them with templates
template<typename T>
class class1
{
public:
class1(T callback): mCallback{std::move(callback)} {}
private:
const T mCallback
};
template<typename T>
auto makeClass1(T&& callback) {
return class1<std::decay_t<T>>{std::forward<T>(callback)};
}
int main()
{
auto thiscode = [] (int id)
{
std::cout<<"callback from..." << id << std::endl;
};
auto c1 = makeClass1(thiscode);
}
Or alternatively, you can hold them with std::function
:
class class1
{
public:
class1(std::function<void(int)> callback);
private:
const std::function<void(int)> mCallback
};
int main()
{
auto thiscode = [] (int id)
{
std::cout<<"callback from..." << id << std::endl;
};
class1 c1 = class1(thiscode);
}
Upvotes: 3