如何在 Scala 中提取列表的第三个元素

How to extract 3rd element of the list in Scala

 def third_list[A](ls: List[A]): A = {
     // Code can be changed here
    return List(ls(2)) //Error line for return type
  }


  val l1 = List(1, 2, 3, 4)
  println(third_list(l1))
  println(third_list(List(1,2,(3,4,5), 6, 7)))

我需要 return 列表的第 3 个元素遵循 return 类型标准。

我收到类型不匹配错误:

Required A found list[A]

不应该 ls(2) return 一个元素类型吗?

您正在 return 一个包含类型 A 元素的列表,因此您 return 一个列表 [A] 值,但是您为该方法设置的 return 类型是A,他们不匹配。

您已将 third_list 的 return 类型声明为 A,但您正在提取类型 A (ls(2)) 的元素,包装它在一个新列表中(List(ls(2)),然后 return 取而代之。此外,如果列表中没有至少 3 个元素,您的代码将失败。处理该问题的一种方法可能是 return 一个 Option[A] 而不是 A。类似下面的东西:

def third_list[A](ls: List[A]): Option[A] = ls match {
  case _ :: _ :: third :: _ =>
    Some(third)
  case _ =>
    None
}

编辑:

使用 Option 来处理第三个元素不存在的情况是理想的方法,因为它告诉此方法的调用者它不能保证 return 的值为 A.

但是,如果您必须保留原始方法签名,则可以在不存在第三个元素的情况下抛出异常:

def third_list[A](ls: List[A]): A = ls match {
  case _ :: _ :: third :: _ =>
    third
  case _ =>
    throw new RuntimeException(s"Error occurred access third element of list. List had length ${ls.length}.")
}

或者可以要求方法的调用者在第三个元素不可访问的情况下提供默认值,尽管在这种情况下您再次更改方法签名,因此建议 Option

def third_list[A](ls: List[A], default: => A): A = ls match {
  case _ :: _ :: third :: _ =>
    third
  case _ =>
    default
}

值得重申的是,将 return 类型设为 Option 类型仍然是最佳实践方法。 See this official Scala lang documentation on functional error handling.

问题的简单答案是使用 lift:

def third_list[A](ls: List[A]): Option[A] =
  ls.lift(2)

这 returns 和 Option 因为您真的希望您的代码能够工作,即使列表没有三个元素。处理 Option 内的数据或使用 getOrElse 指定默认值。