"type mismatch" 在列表上使用 :+ 方法时出错

"type mismatch" error while using :+ method on a List

我刚开始学习scala。我试图编写一个函数来反转任意类型的列表。

代码如下:

def reverse [A] (l:List[A]):List[A] = {
     val size:Int = lenList(l) // i have implemented this func separately
     if (l.isEmpty) List()
     else {
              var newList = List()
              for (i <- 1 to size)
              {
                  var temp = l(size - i)
                  newList = newList :+ temp //type mismatch error here
              }
     newList
    }
   }'

以上代码编译时出现的错误:

当我将 newList 声明更改为 var newList = List[A]()(与作为参数传递的列表类型相同)时,代码编译成功。

我的问题是:

  1. newList 是类型 List[Nothing]temp 是 [= 的元素时,为什么行 newList = newList :+ temp 上存在类型不匹配20=]?

  2. 当语句中没有涉及 List[A] 类型时,为什么编译器会说 Found:List[A]

  3. 谁能告诉我发生这种类型不匹配错误的原因吗?

  4. 另外我想知道为什么我改声明的时候代码会编译?

  5. 我的声明对最初抛出错误的语句有什么影响?

我相信在这种情况下下面的错误消息是合理的

found:List[Nothing] 
Required:List[A] 

而不是我遇到的:

found:List[A]
Required:List[Nothing]

由于语句中使用了 List[Nothing] 类型的 newList 并且我尝试附加的元素是 type A 那么可以理解所需的类型应该是 List[A].

当你这样做时:

var newList = List()

newList 的类型是 List[Nothing]。如果您是 scala 的新手,Nothing 是所有其他类型的子类型。实际上它有点无用,当我们必须向它写入任何数据时。我们会看到为什么会这样。

当您执行 newList :+ temp 时,您将临时文件(A 类型)附加到 List[Nothing]。所以对于编译器来说,类型推断预测这个新列表必须是 List[A] 类型。 (想象一下,如果你创建了一个狮子、鸟类和蛇的列表,你不会把这个新列表称为动物列表吗?)

所以生成的列表是List[A]类型的。然后您尝试将其分配给自身 (newList =)。其中原本是一个List[Nothing]。在 scala 中,使用 var,您可以更改值但不能更改类型。在这里,我们试图将 newList 的类型从 List[Nothing] 更改为 List[A]

因此出现错误及其解释

使用newList.+:(temp)附加到列表