谁说Python不能尾递归优化

继前面理解了CPS后,尾递归的概念深化了我对函数式编程的理解。那Python作为一个不那么正宗的函数式语言。
自己能对尾递归优化么?我们来看个例子。

def fib(count, cur=0, next_=1):
    if count <= 1:
        return cur
    else:
        # Notice that this is the tail-recursive version
        # of fib.
        return fib(count-1, next_, cur + next_)

print fib(996)
#执行结果
RuntimeError: maximum recursion depth exceeded
>>>

看来就算我们的函数已经是尾递归形式了,堆栈还是会层层累计,996次就崩溃了。
再来看这个版本

def fib(count, cur=0, next_=1):
    if count <= 1:
        yield cur
    else:
        # Notice that this is the tail-recursive version
        # of fib.
        yield fib(count-1, next_, cur + next_)
print fib(996)

这样我们用关键字Yield代替Return把原来的函数变成了生成器。这样如果你只传入参数解释器是不会真正运行的!!!
#执行结果
<generator object fib at 0x02B00D00>
那我们怎么办呢,这里我们使用的技术称为Trampline,我们用一个方法让它不断执行生成器的next(),达到我们的目的。

import types

def tramp(gen, *args, **kwargs):
    g = gen(*args, **kwargs)
    while isinstance(g, types.GeneratorType):
        g=g.next()
    return g
print tramp(fib, 996)
#执行结果    
3919377061614427623668052985592742430389065042819420493170692719480242247392252775480208752179017313071371501566248877239254299341332131655760767122899079117071192049598939666199865808814650408864891823186505

成功了,堆栈不会溢出了,尾递归被真的优化了!

推荐阅读更多精彩内容