[nem-en] An idea on tail recursible functions
Snaury
snaury at gmail.com
Mon Jul 3 08:34:48 CEST 2006
I don't know if this idea already was in people minds, but anyway.
Imagine that you have a tail recursible function local to some method,
which you need to call twice. Like this:
def seq(from, to, r = [])
if(from == to)
r.Rev() // br -> ** (*)
else
seq(from + 1, to, from :: r)
def a = seq(1, 10)
// (**)
def b = seq(10, 20)
// (**)
System.Console.WriteLine(a.ToString())
System.Console.WriteLine(b.ToString())
Now, I understand that in normal circumstances parameters to the
function become locals and upon return (marked with *) it just
branches to from where it was called (**). Thus, because there are two
places where it can return, it becomes a method. But what I think is
possible is that this function actually can be called more than once
and still stay within outer function, i.e.:
mutable _return_to
// br -> *
def seq(from, to, r = [])
if(from == to)
r.Rev()
// OpCodes.Ldloc _return_to
// OpCodes.Switch
// | 0 => br -> **
// | 1 => br -> ***
else
seq(from + 1, to, from :: r)
// (*)
_return_to = 0
def a = seq(from, to)
// (**)
_return_to = 1
def b = seq(from, to)
// (***)
And because constructs like this are prohibited:
def a(i)
b(i)
def b(i)
a(i - 1)
It seems we might as well not worry about call graph (otherwise locals
corruption could happen). After this, the only situations when local
function should become a method are
a) it is used as/in lambda (however, when it is used *only* in
lambda and not in outer function, its body might be moved into lambda)
b) it has recursion and it not tail recursion
I don't think I have enough knowledge to implement it on my own, but
if anyone with more skills likes an idea, it would be good to
implement. :)
P.S.
If I don't see some gotchas here, please tell me so, otherwise I'm
willing to sumbit it as a feature request to bugs database.
More information about the devel-en
mailing list