从阵列到WrappedArray隐式转换时的模式匹配
在这个例子中不会发生:从阵列到WrappedArray隐式转换时的模式匹配
scala> val a: Seq[Int] = Array(1,2,3)
a: Seq[Int] = WrappedArray(1, 2, 3)
隐式转换发生,Array
转换为WrappedArray
延伸Seq
,如下解释:Arrays Scala Doc
但这里:
object MyObject {
def main(args: Array[String]): Unit = {
val a = Array(1,2,3)
// val a: Seq[Int] = Array(1,2,3) if added explicitly works
val result = a match {
case Seq(
first,
second,
third
) => (first, second, third)
}
println(result)
}
}
该代码失败:
Error:(9, 15) scrutinee is incompatible with pattern type;
found : Seq[A]
required: Array[Int]
case Seq(
隐式转换不会发生,为什么?
布拉克埃米尔给了一个理由来模式匹配不允许隐式转换(以下是从www.scala-archive.org报价)的语言设计决定:
1)类型检查模式依赖于静态信息(喜欢到处 其他在编译器中)。在模式的情况下,“预期类型”是向下传播的,以便键入可变绑定模式,并且更多地通常验证该模式是有意义的。当然,预期类型开始于监票人(也就是选择器 表达式,也就是匹配的内容)。
2)模式匹配的翻译使用(几乎)每种方式可以避免多余的类型测试 。这意味着源代码中存在的案例 被“压缩”成一种决策树 图。这后来被翻译成代码。
输入隐式转换。让监票人的类型不同 那么模式意味着我们不能在模式中使用预期的类型。 因此,我们必须键入检查模式,而不管检查者的类型为 。
这可能仍然是可行的(小心在这里,谁可以预见毛发 与序列模式的互动等)。我们可以说,模式具有独立于预期类型的 类型,并且类型检查将会看到 监察者的类型是否符合模式类型 (可能在应用某种隐式转换之后)。
但是这原来是一个非规范。
implicit def fbTypeToFoo ...
implicit def fbTypeToBar ...
fb match {
case Foo(...) =>
case Bar(...) =>
}
什么似乎真的需要是“需要通过”申请的意见,这意味着 “内部”的模式匹配。
这与本任务执行任务2)的冲突。在存在 隐式转换的情况下,模式匹配的任务实际上会将一个 级别推得更深,因为最外层的模式将始终匹配(毕竟有一个 转换)。这是很烦人的实现和 指定,因为有花纹和图案,而不从scrutinee类型隐式转换 可能会被混合,就像在
implicit def FooToBar...
myFoo match {
case Foo(...)
case Bar(...)
case Foo(...)
}
假设有一个顶级“富“永远不会进入”酒吧“的情况 现在是无效的(毕竟有转换)。基本上失去了所有最优层次的希望。尽管当前匹配器 将加入模式1和3的其余部分,但带有隐式调用的假设匹配器 不能设计为这样,因为它违反了第一个匹配策略 。
作为一个实用的解决方案,您可以随时“检索”您的数组。 'toSeq'方法不会构造一个新的集合,所以它只会包装数组。来源:http://www.scala-lang.org/api/2.12.1/scala/Array.html#toSeq:Seq [A] –