【发布时间】:2014-01-14 20:31:49
【问题描述】:
我正在学习 Scala,在此过程中,我遵循了 Brien (http://www.knowing.net/index.php/2006/06/16/15-exercises-to-know-a-programming-language-part-1/) 的 15 个练习。在第二个练习中,我应该实现 Haar 转换。我实现了大部分
但是在尾递归的返回值上挣扎了几个小时。由于编译器不编译 ++ - 或者更确切地说是 haar(averages) ++ haar(averagesD) 行。
- 我在递归函数中做错了什么?
- 您能否就我的代码提供其他反馈?
代码:
import scala.collection.mutable.ListBuffer
import scala.annotation.tailrec
object haarWavelet2 {
def avg(tpl:Tuple2[Double, Double]):Double = (tpl._1 + tpl._2) / 2.
def avgD(tpl:Tuple2[Double, Double]):Double = (tpl._1 - tpl._2) / 2
def total_avg(nums:ListBuffer[Double]):Double = nums.sum / nums.length
@tailrec
def haar(nums:ListBuffer[Double]):ListBuffer[Double] = {
if (nums.length == 1) {return nums}
val buffer = new ListBuffer[Tuple2[Double, Double]]
for (i <- 0 to nums.length-1 by 2) buffer.append((nums(i), nums(i+1)))
val averages = for(tpl <- buffer) yield avg(tpl)
val averagesD = for(tpl <- buffer) yield avgD(tpl)
haar(averages) ++ haar(averagesD) // does not compile
}
def main(args: Array[String]): Unit = {
print(haar(ListBuffer(8., 5., 6., 2.)))
}
}
【问题讨论】:
-
我在递归函数中做错了什么?您正在执行 tail 递归。根据定义 tail 递归调用必须是要评估的 last 一个语句,但在您的情况下,最后一个语句是
++(进行递归调用,实际上是两个他们,然后才处理结果) -
有什么理由在这里使用可变的
ListBuffer?递归函数对我来说是“不可变的”。Vector的追加速度非常好。
标签: scala tail-recursion