2012-09-09 76 views
5

有人可以解釋爲什麼下面的代碼編譯?斯卡拉模式匹配和類型推斷

Option("foo") match { 
    case x: List[String] => println("A") 
    case _ => println("B") 
} 

這給我一個關於類型擦除的(預期的)警告,但它仍然編譯。我預計這會引發類型錯誤,就像我在"foo"而不是Option("foo")上匹配一樣。

謝謝!

+1

看起來像一個錯誤。我會報告它。 – sschaef

回答

2

我會假設編譯器將OptionList同時視爲Product,這就是編譯它的原因。正如你所說,預計關於類型擦除的警告。下面是一個使用另一種產品的一個實例:

scala> Option("foo") match { 
| case x: Tuple2[String,String] => println("TUPLE") 
| case x: List[String] => println("LIST") 
| case _ => println("OTHER") 
| } 
<console>:9: warning: non variable type-argument String in type pattern (String, String)  is unchecked since it is eliminated by erasure 
      case x: Tuple2[String,String] => println("TUPLE") 
       ^
<console>:10: warning: non variable type-argument String in type pattern List[String] is unchecked since it is eliminated by erasure 
      case x: List[String] => println("LIST") 
       ^

UPDATE W/R/T case類(因爲下面的註釋):

scala> case class Foo(bar: Int) 
defined class Foo 

scala> val y: Product = Foo(123) 
y: Product = Foo(123) 
+0

看來它與'​​Product'沒有任何關係。我用我自己的case類取代了'Option(「foo」)''參數,並且沒有錯誤。 – ghik

+2

錯誤,案例分類自動擴展產品。請參閱響應編輯。 – timothy

+1

好吧,但它並不一定是案例類。通常的非最終課程也不會導致錯誤。 – ghik

0

我注意到,顯示錯誤當類的你匹配的價值被宣佈爲最終的(我們知道String是最終的)。如果沒有它,我仍然不知道爲什麼沒有錯誤。

4

的代碼註釋,所以讓我們花點時間來品嚐的是:

/** If we can absolutely rule out a match we can fail early. 
    * This is the case if the scrutinee has no unresolved type arguments 
    * and is a "final type", meaning final + invariant in all type parameters. 
    */ 

注意,無不是終點,例如。我知道,對吧?

如果你曾經嘗試scalac -Ypatmat調試,這裏的評論可能會幫助:

https://github.com/scala/scala/pull/650

可達性幾近伸手可及:

https://issues.scala-lang.org/browse/SI-6146

,但我沒有看到任何關於可能有什麼可以警告的承諾。出於性能原因?人們也可以說,爲什麼要警告一個實例[Foo [_]]?

現在,規範章節8.2-8.4激發了爲什麼與Foo [a]匹配很有趣(因爲獲得了邊界)。我想我會再讀一遍。喝完咖啡後。

trait Foo[+A] 
final class Fuzz[+A] extends Foo[A] 
final object Fooz extends Foo[Nothing] 
object Futz extends Foo[Nothing] 

//error 
Fooz match { 
    case x: List[_] => println("A") 
    case _ => println("B") 
} 
//no error 
Futz match { ... } 
+0

不錯,認爲這將是模式匹配器的一些怪癖,但昨晚看不到它:-) – timothy