tag:blogger.com,1999:blog-13960885.post8876949282511267395..comments2024-03-26T02:03:01.072-07:00Comments on C++ Truths: Creating Recursive Lambdas ... and returning them too!Sumanthttp://www.blogger.com/profile/11957855386259543653noreply@blogger.comBlogger8125tag:blogger.com,1999:blog-13960885.post-9329434393128188192017-06-24T09:53:26.841-07:002017-06-24T09:53:26.841-07:00thanks for sharing
gclubthanks for sharing<br /><a href="https://www.gesmotos.com" rel="nofollow">gclub</a>Anonymousnoreply@blogger.comtag:blogger.com,1999:blog-13960885.post-69355350775447304032016-02-11T06:03:19.687-08:002016-02-11T06:03:19.687-08:00Here's an interesting use-case: Recursive func...Here's an interesting use-case: Recursive function often need to access some global constants and variables. You could pass them as arguments, but that messes up the signature and can also lead to to typo errors. OTOH, nobody likes or wants global data. It would be great f you could define a function that returns a lambda with its own "closure", i.e. the outer function defines function local variables that can be accessed by the recursive lambda(s) directly (or as captured) without needing to specify them in the signature. This keeps the data hidden while keeping the functions simple. <br /><br />A.S.https://www.blogger.com/profile/16913096271184629282noreply@blogger.comtag:blogger.com,1999:blog-13960885.post-80564055515404742942014-01-21T17:18:24.340-08:002014-01-21T17:18:24.340-08:00Wtf? Blogger removed my template parameters, excep...Wtf? Blogger removed my template parameters, except the >.jacobgypsumnoreply@blogger.comtag:blogger.com,1999:blog-13960885.post-77246192952207469392014-01-21T15:09:27.139-08:002014-01-21T15:09:27.139-08:00I wrote an even more ugly variant that does not us...I wrote an even more ugly variant that does not use magic values (though still requires using a constant parameter with which the function is known to return fast). I put a shared_ptr in the lambda that shows whether it is the first run. Using this, I reset both shared_ptr's in the copy that refers to itself.<br /><br />std::function fib_generator(int a, int b)<br />{<br /> std::shared_ptr> fib {new std::function};<br /> std::weak_ptr> wfib(fib);<br /> std::shared_ptr first_run {new bool {true}};<br /> *fib=[wfib, fib, first_run, a, b](int n) mutable<br /> {<br /> if (first_run && *first_run)<br /> {<br /> fib.reset();<br /> *first_run=false;<br /> first_run.reset();<br /> }<br /> std::shared_ptr> sfib=wfib.lock();<br /> return (n <= 2)? ((n==1) ? a : b) : (*sfib)(n-1) + (*sfib)(n-2);<br /> };<br /> std::function rfib=*fib;<br /> (*fib)(1);<br /> return rfib;<br />}<br /><br />Anyone has a nicer one?jacobgypsumnoreply@blogger.comtag:blogger.com,1999:blog-13960885.post-28013513539552515842014-01-21T15:06:23.674-08:002014-01-21T15:06:23.674-08:00I wrote a solution that does not use a custom clas...I wrote a solution that does not use a custom class, returns a recursive function itself, and works for stateful recursive functions too. The idea is that if we need to use the variable after our function returns, we need to create it on the heap. Since we don't want to leak memory, we use smart pointers. I put both a shared_ptr and a weak_ptr in the lambda. Then, using a magic parameter, I reset the shared_ptr in the copy that refers to itself, while it is retained in the copy I return.<br /><br />std::function fib_generator(int a, int b)<br />{<br /> std::shared_ptr> fib {new std::function};<br /> std::weak_ptr> wfib(fib);<br /> *fib=[wfib, fib, a, b](int n) mutable<br /> {<br /> if (n==-1) { fib.reset(); return 0; }<br /> std::shared_ptr> sfib=wfib.lock();<br /> return (n <= 2)? ((n==1) ? a : b) : (*sfib)(n-1) + (*sfib)(n-2);<br /> };<br /> std::function rfib=*fib;<br /> (*fib)(-1);<br /> return rfib;<br />}<br /><br />int main()<br />{<br /> auto fib1=fib_generator(1, 1);<br /> auto fib2=fib_generator(2, 2);<br /> printf("%i\n", fib1(10));<br /> printf("%i\n", fib2(10));<br /> return 0;<br />}<br />jacobgypsumnoreply@blogger.comtag:blogger.com,1999:blog-13960885.post-4968446146124383182014-01-21T13:50:15.711-08:002014-01-21T13:50:15.711-08:00If the lambda is not stateful, it is enough to dec...If the lambda is not stateful, it is enough to declare it static (so that you can return it as reference), isn't it?jacobgypsumnoreply@blogger.comtag:blogger.com,1999:blog-13960885.post-46041381328670134302013-10-17T10:23:42.505-07:002013-10-17T10:23:42.505-07:00I'd like to be able to create (sort of) recurs...I'd like to be able to create (sort of) recursive lambdas, but the context I want them doesn't allow this solution. I'm passing a lambda directly to a function, so I can't declare any variable at the same time. Passing lambdas directly is sort of where lambdas shine. If you have to write the expression elsewhere to declare a variable you might just as well just go with an entirely separate named functor or function. Useful recursive lambdas (or just a lambda that needs to refer to itself, say, to place itself on an asynchronous queue) really requires a keyword or something so that the lambda can literally refer to itself.Anonymousnoreply@blogger.comtag:blogger.com,1999:blog-13960885.post-35812219783163233452013-10-17T00:04:27.819-07:002013-10-17T00:04:27.819-07:00While this is a nice trick, recursive functions ar...While this is a nice trick, recursive functions are very inefficient, so it's best not to use them at all.Levnoreply@blogger.com