我看到 C++11 文档 ( http://en.cppreference.com/w/cpp/language/lambda ) 中的 lambda 表达式声明支持按值捕获和引用,但不支持右值引用。我能找到的与此相关的最接近的问题是:How to capture a unique_ptr into a lambda expression? ,但我的用例似乎不需要使用std::bind.
#include <iostream>
#include <memory>
class Foo
{
public:
explicit Foo(int value = 0) : mValue(value) {}
// The following items are provided just to be explicit
Foo(Foo &&other) = default;
Foo &operator=(Foo &&other) = default;
Foo(const Foo &other) = delete;
Foo &operator=(const Foo &other) = delete;
~Foo() {}
int mValue;
};
void bar(std::unique_ptr<Foo> f)
{
std::cout << "bar: " << std::dec << f->mValue << "\n";
}
int main()
{
{
std::unique_ptr<Foo> f(new Foo(22));
std::cout << "main: " << std::hex << f.get() << "\n";
// Call the bar function directly (requires using std::move)
bar(std::move(f));
std::cout << "main: " << std::hex << f.get() << "\n";
}
{
std::unique_ptr<Foo> f(new Foo(99));
std::cout << "main: " << std::hex << f.get() << "\n";
// Lamda expression captures 'f' by reference and then calls the bar function (again, requires using std::move)
auto fn = [&f](){ bar(std::move(f)); };
fn(); // Execute the closure
std::cout << "main: " << std::hex << f.get() << "\n";
}
return 0;
}
Run Code Online (Sandbox Code Playgroud)
main: 0x92e010
bar: 22
main: 0
main: 0x92e010
bar: 99
main: 0
Run Code Online (Sandbox Code Playgroud)
通过检查输出,该程序似乎运行正确(即观察到的结果符合我的预期。但是,我有以下问题。
bar直接调用函数的代码?
std::move捕获的引用的任何内容(即,我想确保这不会发生冲突undefined behavior或类似的不良结果)。std::move在捕获的引用上使用”,那么执行此操作的正确方法是什么(例如解决std::bind方案等)?使用闭包是否等同于直接调用 bar 函数的代码?
是的,它们在这段代码中是等效的。捕获的引用在我能想到的任何方面都没有什么特殊之处:只要f在范围内并且可以从中移动,您就拥有完全定义的行为。
| 归档时间: |
|
| 查看次数: |
330 次 |
| 最近记录: |