Scala函数字面量中必须使用case关键字的场景有哪些?
Scala函数字面量case关键字使用规则解答
错误本质
编译报错的核心原因是函数参数数量不匹配:
- 无case的写法
(x,y) => Coord(x,y)会被编译器识别为接受2个Int参数的多参函数,类型为(Int, Int) => Coord List[(Int, Int)]的map方法要求传入接受1个(Int, Int)元组参数的单参函数,类型为((Int, Int)) => Coord
二者类型不兼容,因此触发编译错误。
case关键字生效的原因
{ case (x,y) => Coord(x,y) }是Scala偏函数字面量的语法糖,会被识别为入参为(Int, Int)元组的单参函数,执行时自动对输入元组做模式匹配,解构出x、y两个成员,刚好匹配map要求的入参类型,因此可以正常运行。
必须使用case关键字的场景
1. 对函数单入参做模式解构
只要需要直接拆解入参的内部成员,无论入参是元组、样例类、集合还是其他支持模式匹配的类型,都可以使用case语法。该规则不是元组独有的特殊设计,比如对样例类列表做字段提取也可以用相同写法:
val coordList: List[Coord] = List(Coord(1,2), Coord(3,4)) coordList.map{ case Coord(x, _) => x } // 提取所有Coord的x字段
如果不想使用case语法,也有两种替代实现方式:
- 手动访问元组成员:
data.map(t => Coord(t._1, t._2)) - 把多参函数转换为接受元组的单参函数:
val createCoord = (x: Int, y: Int) => Coord(x,y) data.map(createCoord.tupled)
2. 定义多分支偏函数
如果需要对入参做条件匹配、仅处理符合要求的输入(比如配合collect方法同时完成过滤和转换),必须用case定义不同的匹配分支:
// 仅保留x大于2的元组,转换为Coord data.collect{ case (x,y) if x > 2 => Coord(x,y) }
内容的提问来源于stack exchange,提问作者nemoo
相关产品推荐
相关产品推荐

