我正在學習Scala,並在此過程中遵循Brien的15個練習(http://www.knowing.net/index.php/2006/06/16/15-exercises-to-know-a-programming-language-part-1/)在第二個練習中,我應該實施哈爾變換。我實現了它的大部分 ,但用尾遞歸的返回值掙扎了好幾個小時。由於編譯器不編譯++
- 或更確切地說是行haar(averages) ++ haar(averagesD)
。Scala:尾遞歸和ListBuffer
- 我在做什麼錯在遞歸函數?
- 你能否就我的代碼給我其他反饋?
代碼:
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 **遞歸調用必須是要評估的最後一個**語句,但在您的情況下,最後一個語句是'++'(進行遞歸調用,實際上是其中的兩個,然後才處理結果) –
你在這裏使用可變的'ListBuffer'的任何原因?遞歸函數尖叫「不可變」給我。 'Vector'具有非常好的追加速度。 – KChaloux