Scala 为什么在map函数中使用函数args中的case进行模式匹配更好
Scala说“模式匹配的函数参数中的用例”Scala 为什么在map函数中使用函数args中的case进行模式匹配更好,scala,Scala,Scala说“模式匹配的函数参数中的用例” 为什么前者更好 好吧,后者根本不起作用 scala> val xs = List(1, 2, 3) xs: List[Int] = List(1, 2, 3) scala> val ys = List(4, 5, 6) ys: List[Int] = List(4, 5, 6) scala> (xs zip ys).map((x,y) => x*y) <console>:10: error: missing pa
为什么前者更好 好吧,后者根本不起作用
scala> val xs = List(1, 2, 3)
xs: List[Int] = List(1, 2, 3)
scala> val ys = List(4, 5, 6)
ys: List[Int] = List(4, 5, 6)
scala> (xs zip ys).map((x,y) => x*y)
<console>:10: error: missing parameter type
Note: The expected type requires a one-argument function accepting a 2-Tuple.
Consider a pattern matching anonymous function, `{ case (x, y) => ... }`
(xs zip ys).map((x,y) => x*y)
^
<console>:10: error: missing parameter type
(xs zip ys).map((x,y) => x*y)
^
scala> (xs zip ys).map { case (x,y) => x*y }
res0: List[Int] = List(4, 10, 18)
(x,y)=>x*y
是以下内容的语法糖(我假设我们讨论的是整数):
集合上的map
采用了aa=>B
(将其分解为Function1[a,B]
),这是与Function2
完全不同的类型。因此,在示例中不使用后一个版本的一个很好的理由是编译器不会接受它
如果您有一个方法实际使用了函数2
,则可以使用以下任一方法:
scala> val pair = (List(1, 2, 3), List(4, 5, 6))
pair: (List[Int], List[Int]) = (List(1, 2, 3),List(4, 5, 6))
scala> pair.zipped.map { (x, y) => x * y }
res0: List[Int] = List(4, 10, 18)
scala> pair.zipped.map { case (x, y) => x * y }
res1: List[Int] = List(4, 10, 18)
case
版本之所以有效,是因为编译器支持Function2
的函数文本语法中的模式匹配。一般来说,我个人更喜欢(x,y)=>x*y
语法(即,当您的方法需要函数2
并且您不需要进行任何其他模式匹配时)。使用模式匹配,您可以显式指定要映射的输入参数的形式(类型)(一个接受元组-2的单参数函数); 在第二种情况下(没有模式匹配),需要显式指定类型(因为它与2参数函数具有相同的形式)。您只需在REPL(scala 2.11.6)中键入即可看到这一点:
scala>val xs=List(1,2,3,4)
xs:List[Int]=List(1,2,3,4)
scala>val ys=List(1,2,3,4)
ys:List[Int]=List(1,2,3,4)
scala>(xs-zip-ys)映射{case(x,y)=>x*y}
res0:List[Int]=List(1,4,9,16)
scala>(xs-zip-ys)映射((x,y)=>x*y)
:10:错误:缺少参数类型
注意:预期类型需要一个单参数函数
二元组。
考虑一个匹配匿名函数的模式:{{(x,y)=}}
(x,y)=>x*y)
^
:10:错误:缺少参数类型
(x,y)=>x*y)
你知道为什么pair.zipped
和(pair.\u 1 zip pair.\u 2)
的工作方式不同吗?pair.zipped
的设计目的是支持优化,它不需要构建一堆元组,而这些元组将立即被丢弃。
import Function.tupled
(xs zip ys) map tupled { (x,y) => x*y }
new Function2[Int, Int, Int] {
def apply(x: Int, y: Int): Int = x * y
}
scala> val pair = (List(1, 2, 3), List(4, 5, 6))
pair: (List[Int], List[Int]) = (List(1, 2, 3),List(4, 5, 6))
scala> pair.zipped.map { (x, y) => x * y }
res0: List[Int] = List(4, 10, 18)
scala> pair.zipped.map { case (x, y) => x * y }
res1: List[Int] = List(4, 10, 18)
scala> val xs = List(1,2,3,4)
xs: List[Int] = List(1, 2, 3, 4)
scala> val ys = List(1,2,3,4)
ys: List[Int] = List(1, 2, 3, 4)
scala> (xs zip ys) map { case (x,y) => x*y }
res0: List[Int] = List(1, 4, 9, 16)
scala> (xs zip ys) map ((x,y) => x*y)
<console>:10: error: missing parameter type
Note: The expected type requires a one-argument function accepting
a 2-Tuple.
Consider a pattern matching anonymous function, `{ case (x, y) => }`
(xs zip ys) map ((x,y) => x*y)
^
<console>:10: error: missing parameter type
(xs zip ys) map ((x,y) => x*y)