C++ lambda 如何/能否保留内部状态?

问题描述 投票:0回答:4

我有一个基本的 lambda,如下所示:

auto l = [](){
  int i = 0;
  cout << i++;
}

多次调用此函数,将继续打印 0。如何保留 i?我可以在没有函子的情况下做到这一点吗?

c++ lambda
4个回答
26
投票

根据您想要使用此 lambda 执行的操作,您可以考虑以下替代方案:

auto exec = [i = 0]() mutable { cout << ++i << ' '; };
exec();  // 1
exec();  // 2
auto exec2 = exec; // copy state of lambda
exec2(); // 3
exec();  // 3

使用

[]() { static int i = 0; cout << ++i << ' '; };
将会导致打印序列
1 2 3 4

实例


21
投票

尝试将 lambda 视为带有

operator()
的类。您将如何在课堂上保留状态?有会员。捕获在这里是等效的。

#include <iostream>
auto l = [i=0]()mutable{
  std::cout << i++<<std::endl;
};
auto l2=l;
int main(){
  l(); // 0
  l(); // 1
  l(); // 2
  l2(); // 0
  l2(); // 1
  l(); // 3
  std::cout << '\n';
}

5
投票
 auto l = [](){
   static int i = 0;
// ^^^^^^
   cout << i++;
 }

应该可以解决您的担忧。

一般来说,如果不使用局部 static 变量,函数就无法保留

内部状态
。实际上与使用 lambda 没有什么区别。


如果你想计算副本数,你可以使用普通函子类实现,如@Revolver_Ocelot建议


2
投票

如果您希望

i
保留其价值,那么您有三个选择:

  1. i
    声明为全局变量(不好)。
  2. 每次都将
    i
    的先前值传递给函数(更好)。
  3. i
    声明为
    static
    变量(最佳)。

    auto l = []() { static int i = 0; cout << i++ << endl; };
    l(); l(); l();
    

    这将给出输出:

    0
    1
    2
    
© www.soinside.com 2019 - 2024. All rights reserved.