Call lambda without binding it to id

Looking at some internet platforms I ran into this problem:

"Implement a recursive anonymous function in your favorite language"

Obviously, it is easy to use the std :: function / function pointer.

I'm really wondering if this is possible without associating lambda with an identifier?

Something like (ignoring the obvious infinite recursion):

[](){ this(); }(); 
+7
source share
4 answers

Of course, in C ++, to call any function, you have to bind it to an identifier somewhere, simply because of syntactic restrictions. But, if you accept the parameters as not sufficiently named, then you can create a version of y-combinator in C ++ that will look good without being β€œnamed”.

Now this is really ugly because I don't know how to make a typedef for a recursive lambda . So he just uses a lot of abuse. But it works and prints FLY!! until segfault happens due to.

 #include <iostream> typedef void(*f0)(); typedef void(*f)(f0); int main() { [](fx) { x((f0)x); } ([](f0 x) { std::cout<<"FLY!!\n"; ((f)x)(x); }); } 

The two lambdas are unnamed in the sense that none of them are assigned anywhere. The second lambda is a real workhorse, and it basically calls itself using the first lambda to get a link to itself as a parameter.

Here's how you could use this to do a β€œuseful” job:

 #include <iostream> typedef int param_t; typedef int ret_t; typedef void(*f0)(); typedef ret_t(*f)(f0, param_t); int main() { /* Compute factorial recursively */ std::cout << [](fx, param_t y) { return x((f0)x, y); } ([](f0 x, param_t y) { if(y == 0) return 1; return y*((f)x)(x, y-1); }, 10) << std::endl; } 
+5
source

Are you allowed to cheat?

 void f(){ []{ f(); }(); } 

Recursive - indirectly, at least.

Otherwise, no, you can not refer to the lambda itself without giving it a name.

+3
source

No identifier for functions / methods , close enough or not !?

 struct A { void operator()() { [&]() { (*this)(); }(); } }; 

To call

 A{}(); // Thanks MooningDuck 
+1
source

I seem to have come up with my solution:

 #include <iostream> int main() { std::cout<<"Main\n"; [&](){ std::cout<<"Hello!\n"; (&main+13)(); }(); } 

The first call to cout is present only to show that it does not call the main one.

I came up with 13 trial and error biases if anyone can explain why this value would be great.

0
source

All Articles