强制C ++ 11 lambda捕获变量

时间:2014-09-11 05:52:12

标签: c++ c++11 lambda

假设复制变量具有所需的副作用。我想声明一个复制变量的lambda,但不会使用该变量。这样做的最低要求是什么?

Copiable copyable;

auto lambda1 = [=](){};
auto lambda2 = [copyable](){};
auto lambda3 = [=](){ copyable; }
auto lambda4 = [=](){ volatile copy = copyable; }

lambda1使用隐式捕获,由于正文没有提到copyable,我不相信它实际上会复制它。

lambda2使用显式捕获,似乎根据this,它应该通过副本捕获。是否允许编译器删除副本?有关此问题的另一个讨论,请参见this

lambda3使用隐式捕获,但正文提到了copyable。这是否构成copyable odr-use

lambda4使用隐式捕获并强制另一个volatile副本。我确信这确实会有效,但它的副本数量超过了最低限度。

激励案例:我需要在完成任意数量的lambda调用后运行清理,可能在不同的线程中。我可以通过使用std::shared_ptr和一个运行清理的自定义删除器来实现这一点,并以某种方式将其传递给每个lambda。然后,当所有共享ptrs超出范围时,清理将运行。

修改:lambda3lambda4错过=进行隐式捕获。

1 个答案:

答案 0 :(得分:4)

  

执行此操作所需的最低要求是什么?

按值显式捕获,如lambda2

  

lambda1使用隐式捕获,由于正文并未提及可复制,我不相信它实际上会复制它。

那是对的。变量只有在lambda中 odr-used 时才会被隐式捕获。

  

lambda2使用显式捕获,似乎根据this,它应该通过副本捕获。

那是对的。无论是否使用,都将捕获任何明确捕获的变量。这是您希望确保捕获对象的目的。

  

编译器是否允许删除副本?有关此问题的另一个讨论,请参见this

没有。如果捕获了变量,则将其捕获。该链接并非真正"讨论"那;唯一的答案证实了这种情况,标准中有适当的措辞。

  

lambda3使用隐式捕获但身体提到可复制。这是否构成了可复制的 odr-use

是。 odr-use 的定义是

  

名称显示为可能已评估的表达式的变量是 odr-used ,除非它是满足出现在常量表达式中的要求的对象,并且lvalue-to-rvalue转换是立即的应用。

并且异常不适用,因为它不是常数(因此不能出现在常量表达式中)。 (但请注意,这是不正确的,因为没有默认捕获。)

  

lambda4使用隐式捕获并强制使用另一个volatile副本。我确信这实际上会有效,但它的副本数量超过了最低限度。

实际上;您通过使用该值强制进行隐式捕获,并强制执行额外的复制。这是不必要的,因为lambda2可以满足您的需求。

相关问题