#include <functional>
#include <iostream>
class Foo final
{
public:
Foo() { std::cout << "Default constructor" << std::endl; }
Foo(const Foo&) { std::cout << "Copy constructor" << std::endl; }
Foo(Foo&&) noexcept { std::cout << "Move constructor" << std::endl; }
Foo& operator=(const Foo&)
{
std::cout << "Copy assignment" << std::endl;
return *this;
}
Foo& operator=(Foo&&) noexcept
{
std::cout << "Move assignment" << std::endl;
return *this;
}
std::function<void()> f() const noexcept
{
return [*this]{ g(); };
}
~Foo() noexcept
{
std::cout << "Destructor" << std::endl;
}
private:
void g() const noexcept
{
std::cout << "Hello, World! :-)" << std::endl;
}
};
void f(std::function<void()> cb) noexcept
{
if (cb)
{
cb();
}
}
int main()
{
std::function<void()> cb;
std::cout << '1' << std::endl;
{
Foo foo;
std::cout << '2' << std::endl;
cb = foo.f();
std::cout << '3' << std::endl;
}
std::cout << '4' << std::endl;
f(std::move(cb));
std::cout << '5' << std::endl;
return 0;
}
I2luY2x1ZGUgPGZ1bmN0aW9uYWw+CiNpbmNsdWRlIDxpb3N0cmVhbT4KCmNsYXNzIEZvbyBmaW5hbAp7CnB1YmxpYzoKCUZvbygpIHsgc3RkOjpjb3V0IDw8ICJEZWZhdWx0IGNvbnN0cnVjdG9yIiA8PCBzdGQ6OmVuZGw7IH0KCUZvbyhjb25zdCBGb28mKSB7IHN0ZDo6Y291dCA8PCAiQ29weSBjb25zdHJ1Y3RvciIgPDwgc3RkOjplbmRsOyB9CglGb28oRm9vJiYpIG5vZXhjZXB0IHsgc3RkOjpjb3V0IDw8ICJNb3ZlIGNvbnN0cnVjdG9yIiA8PCBzdGQ6OmVuZGw7IH0KCQoJRm9vJiBvcGVyYXRvcj0oY29uc3QgRm9vJikKCXsKCQlzdGQ6OmNvdXQgPDwgIkNvcHkgYXNzaWdubWVudCIgPDwgc3RkOjplbmRsOwoKCQlyZXR1cm4gKnRoaXM7Cgl9CgkKCUZvbyYgb3BlcmF0b3I9KEZvbyYmKSBub2V4Y2VwdAoJewoJCXN0ZDo6Y291dCA8PCAiTW92ZSBhc3NpZ25tZW50IiA8PCBzdGQ6OmVuZGw7CgoJCXJldHVybiAqdGhpczsKCX0KCQoJc3RkOjpmdW5jdGlvbjx2b2lkKCk+IGYoKSBjb25zdCBub2V4Y2VwdAoJewoJCXJldHVybiBbKnRoaXNdeyBnKCk7IH07Cgl9CgkKCX5Gb28oKSBub2V4Y2VwdAoJewoJCXN0ZDo6Y291dCA8PCAiRGVzdHJ1Y3RvciIgPDwgc3RkOjplbmRsOwoJfQoKcHJpdmF0ZToKCXZvaWQgZygpIGNvbnN0IG5vZXhjZXB0Cgl7CgkJc3RkOjpjb3V0IDw8ICJIZWxsbywgV29ybGQhIDotKSIgPDwgc3RkOjplbmRsOwoJfQp9OwoKdm9pZCBmKHN0ZDo6ZnVuY3Rpb248dm9pZCgpPiBjYikgbm9leGNlcHQKewoJaWYgKGNiKQoJewoJCWNiKCk7Cgl9Cn0KCmludCBtYWluKCkKewoJc3RkOjpmdW5jdGlvbjx2b2lkKCk+IGNiOwoJCglzdGQ6OmNvdXQgPDwgJzEnIDw8IHN0ZDo6ZW5kbDsKCXsKCQlGb28gZm9vOwoJCXN0ZDo6Y291dCA8PCAnMicgPDwgc3RkOjplbmRsOwoJCWNiID0gZm9vLmYoKTsKCQlzdGQ6OmNvdXQgPDwgJzMnIDw8IHN0ZDo6ZW5kbDsKCX0KCglzdGQ6OmNvdXQgPDwgJzQnIDw8IHN0ZDo6ZW5kbDsKCWYoc3RkOjptb3ZlKGNiKSk7CglzdGQ6OmNvdXQgPDwgJzUnIDw8IHN0ZDo6ZW5kbDsKCglyZXR1cm4gMDsKfQ==