C++ Lambda函数可绕过const限制,这是否属于编译器Bug?
这不是编译器Bug,是C++ const语义的正常表现
核心原因解析
const Foo&的限制范围:
print_root函数的const Foo& f仅表示引用的Foo对象被视为const,但Foo的成员root本身是非const成员变量。在const对象中,只有非mutable的成员会被强制转为const,而root没有const修饰,因此可以正常调用它的operator()——恰好Lazy类的operator()是const成员函数,完全符合调用规则。lambda捕获的this指针类型:在Foo构造函数中,
this是指向非const Foo对象的指针,lambda默认捕获的this就是Foo*类型(而非const Foo*)。即便后续该Foo对象被const引用绑定,lambda内部保存的依然是最初的非constthis,因此可以自由修改Foo的成员变量x,这完全符合C++的类型规则。
如何禁止这种修改行为
如果要让lambda无法修改Foo的成员,只需给lambda加上const限定符,此时捕获的this会自动转为const Foo*,修改x的代码会直接触发编译错误:
Foo(double _x) : x(_x), root( [this]() const -> double { double a = x/2; std::cout << "Calculating root of " << x << std::endl; for(auto i:iota(0, 1000000000)) a = (a + x/a) / 2; // x = 3; // 此处会编译报错,因为this是const Foo* return a; } ) {}
内容的提问来源于stack exchange,提问作者葛盈泽
相关产品推荐
相关产品推荐

