2017-10-06 98 views
1

我有这个功能,需要两个列表并返回两个列表的总和。斯卡拉递归在多个列表

例子:

def sumOfSums(a: List[Int], b: List[Int]): Int = { 
    var sum = 0 
    for(elem <- a) sum += elem 
    for(elem <- b) sum += elem 
    sum 
} 

够简单了,但是现在我想递归地做到这一点,第二个list参数扔我。

我到目前为止有:

def sumOfSumsRec(a: List[Int], b: List[Int], acc: Int): Int = a match { 
    case Nil => acc 
    case h :: t => sumOfSumsRec(t, acc + h) 
} 

有2个问题在这里:

  1. 我只匹配上的 'a' List
  2. 我得到一个错误当我试图做acc + h,我不知道为什么。

问题:如何递归迭代两个列表以获得它们的总和?

+1

你不能递归合并前的名单?另外对于第二个问题,那是因为你的'sumOfSumsRec'需要3个参数,而不是2个。 – Shaido

回答

2

模式匹配两份名单:

import scala.annotation.tailrec 

def recSum(a: List[Int], b: List[Int]): Int = { 
    @tailrec 
    def recSumInternal(a: List[Int], b: List[Int], acc: Int): Int = { 
    (a, b) match { 
     case (x :: xs, y :: ys) => recSumInternal(xs, ys, x + y + acc) 
     case (x :: xs, Nil) => recSumInternal(xs, Nil, x + acc) 
     case (Nil, y :: ys) => recSumInternal(Nil, ys, y + acc) 
     case _ => acc 
    } 
    } 
    recSumInternal(a, b, 0) 
} 

测试:

recSum(List(1,2), List(3,4,5)) 

产量:

15 

旁注

对于任何未来这篇文章的读者,我认为这个问题主要是教育目的,因此显示递归如何在多个列表上工作,但这绝不是一种习惯的方式。用于任何其他目的,通过各种手段:

scala> val a = List(1,2) 
a: List[Int] = List(1, 2) 

scala> val b = List(3,4,5) 
b: List[Int] = List(3, 4, 5) 

scala> a.sum + b.sum 
res0: Int = 15 

或考虑使用机制,如foldLeftfoldMap

+1

令人惊叹!非常感谢 – Phillip