Dak*_*ksh 52 c++ lambda c++11 c++14 c++17
我试图弄清楚如何在自身中获取lambda函数的地址。这是一个示例代码:
[]() {
std::cout << "Address of this lambda function is => " << ????
}();
Run Code Online (Sandbox Code Playgroud)
我知道我可以在变量中捕获lambda并打印地址,但是我想在执行此匿名函数时就地执行此操作。
有没有更简单的方法?
Yak*_*ont 51
无法直接获取lambda中的lambda对象的地址。
现在,碰巧这经常很有用。最常见的用途是为了递归。
这些y_combinator语言来自您在定义之前无法谈论自己的语言。它可以很容易地在c ++中实现:
template<class F>
struct y_combinator {
F f;
template<class...Args>
decltype(auto) operator()(Args&&...args) const {
return f( f, std::forward<Args>(args)... );
}
template<class...Args>
decltype(auto) operator()(Args&&...args) {
return f( f, std::forward<Args>(args)... );
}
};
Run Code Online (Sandbox Code Playgroud)
现在您可以执行以下操作:
y_combinator{ [](auto& self) {
std::cout<<"Address of this lambda function is => "<< &self;
} }();
Run Code Online (Sandbox Code Playgroud)
其变化形式可以包括:
template<class F>
struct y_combinator {
F f;
template<class...Args>
decltype(auto) operator()(Args&&...args) const {
return f( *this, std::forward<Args>(args)... );
}
template<class...Args>
decltype(auto) operator()(Args&&...args) {
return f( *this, std::forward<Args>(args)... );
}
};
Run Code Online (Sandbox Code Playgroud)
在这里self通过可以称为不传递self作为第一个参数。
第二个匹配我相信的实数y组合器(又名定点组合器)。您想要哪个取决于“ lambda地址”的含义。
Max*_*kin 33
这不是直接可能的。
但是,lambda捕获是类,对象的地址与其第一个成员的地址一致。因此,如果按值捕获一个对象作为第一个捕获,则第一个捕获的地址对应于lambda对象的地址:
int main() {
int i = 0;
auto f = [i]() { printf("%p\n", &i); };
f();
printf("%p\n", &f);
}
Run Code Online (Sandbox Code Playgroud)
输出:
0x7ffe8b80d820
0x7ffe8b80d820
Run Code Online (Sandbox Code Playgroud)
另外,您可以创建一个装饰器设计模式 lambda,将对lambda捕获的引用传递到其调用运算符中:
template<class F>
auto decorate(F f) {
return [f](auto&&... args) mutable {
f(f, std::forward<decltype(args)>(args)...);
};
}
int main() {
auto f = decorate([](auto& that) { printf("%p\n", &that); });
f();
}
Run Code Online (Sandbox Code Playgroud)
ruo*_*ola 25
解决此问题的一种方法是将lambda替换为手写仿函数类。这实际上也是lambda的本质。
然后this,即使没有将函子分配给变量,也可以通过获得地址:
#include <iostream>
class Functor
{
public:
void operator()() {
std::cout << "Address of this functor is => " << this;
}
};
int main()
{
Functor()();
return 0;
}
Run Code Online (Sandbox Code Playgroud)
输出:
Run Code Online (Sandbox Code Playgroud)#include <iostream> class Functor { public: void operator()() { std::cout << "Address of this functor is => " << this; } }; int main() { Functor()(); return 0; }
这样做的好处是,它是100%可移植的,并且非常易于推理和理解。