Scala函数接受不同的类型

时间:2017-09-09 16:09:32

标签: scala

我想弄清楚为什么下面的Scala代码会编译?

trait List[+A]
case object Nil extends List[Nothing]
case class Cons[+A](head: A, tail: List[A]) extends List[A]

def map[A, B](as: List[A])(f: A => B): List[B] = as match {
  case Nil         => Nil
  case Cons(x, xs) => Cons(f(x), map(xs)(f))
}

def tester[A, B](as: List[A])(f1: A => List[B]) = map(as)(f1)

根据我的理解,tester不应该编译,因为map的定义表示它接受两个参数:列表列表A => B类型的函数。

但是,在tester函数中,我的函数f1的类型为A => List[B],因此,由于参数类型不匹配,我认为编译器应该抛出错误。但是代码编译得很好。

你能帮我理解代码编写的原因吗?

2 个答案:

答案 0 :(得分:2)

tester[A,B]方法中,您实际上正在调用map[A, List[B]]

如果您使用不同的类型参数编写测试器方法,那么代码更容易理解,然后调用mapA = CB = List[D]

def tester[C, D](as: List[C])(f1: C => List[D]): List[List[D]] = {
  map[C, List[D]](as)(f1)
}

答案 1 :(得分:1)

我认为您的误解来自于您假设AB类型对于maptester都是通用的,而实际上它们实际上是本地定义。出于此示例的目的,我们将B的{​​{1}}重命名为tester。这意味着C的{​​{1}}实际上将是B