如何优化Scala双递归函数调用

时间:2017-03-10 10:36:17

标签: scala recursion tail-recursion

我试图让这个递归函数起作用:

@tailrec
def rec(n: BigInt): BigInt = {
  if (n == 0) 0
  else if (n == 1) 1
  else (rec(n - 1) + rec(n - 2))
}
  

错误:(13,24)无法优化@tailrec带注释的方法rec:它包含一个不在尾部位置的递归调用         else(rec(n - 1)+ rec(n - 2))

如何优化这种方法以使用tailrec?

1 个答案:

答案 0 :(得分:4)

你将不得不编写一个尾递归辅助函数:

def rec(n: BigInt): BigInt = {
  @tailrec 
  def helper(n: BigInt, previous: BigInt, next: BigInt): BigInt = {
    if (n == 0) previous
    else if (n == 1) next
    else helper(n - 1, next, (next + previous))
  }
  helper(n,0,1)
}

这样,您可以将序列的上一个和下一个值传递给函数,从而只允许对函数进行一次调用。

这是一种常见模式,因为许多递归算法只能通过其他控制流机制(例如:继续传递)进行尾递归。 因子是另一个很好的例子,需要用一个额外的参数编写一个辅助函数来使其尾递归。