递归方程中的尾调用优化

时间:2015-07-24 09:52:56

标签: python optimization tail-recursion

我有以下两个相互递归的函数,

Where

由于python不能很好地处理尾部调用优化,程序员应该将这些函数表示为有状态循环。 python社区使用什么技术将这种方程式转换为显式循环?

或者这些转换是依赖算法的吗?每个递归函数必须单独分析?

递归实施

C1 = xpa, C2 = p and C3 = xpb然后

def obaraSaika(p,s00x,i,j,xpa,xpb):

    if i < 0 or j < 0: return 0

    if i == 0 and j == 0: return s00x

    if i >= 1: return xpa*(obaraSaika(p,s00x,i-1,j,xpa,xpb)) + \
               p*((i-1)*(obaraSaika(p,s00x,i-2,j)) + j*(obaraSaika(p,s00x,i-1,j-1,xpa,xpb) ) )

    if j >= 1: return xpb*(obaraSaika(p,s00x,i-1,j,xpa,xpb)) + \
               p*(i * (obaraSaika(p,s00x,i-1,j-1)) + (j-1)*(obaraSaika(p,s00x,i,j-2,xpa,xpb) ) )

此实现的想法是首先使用i索引遍历树,然后i == 0使用j索引减少树。

1 个答案:

答案 0 :(得分:1)

将任何递归算法转换为非递归等价物很简单。

当您执行递归调用时,您实际执行的操作是将一组参数推送到堆栈。这个堆栈由Python解释器提供。

所以,你在没有递归的情况下重写算法的方式是......你自己管理堆栈!当您进行递归调用时,您将获取所有已传递的参数并将它们推送到堆栈对象上。然后你有一个&#34;驱动程序&#34;循环重复弹出堆栈并执行其中列出的计算。

这类程序的签名是有一个堆栈对象,你用一个初始状态元组/对象,然后一个while len(stack) > 0循环运行,直到你完成

你基本上只做递归会做的事情,但是当你自己管理相关的数据结构时,它会为你提供更好的效率提升机会。

这种特殊类型的转换适用于任何算法。其他的,特别是那些涉及对所讨论的函数的不同调用进行全局状态的那些,是依赖于算法的。