2013-07-21 100 views
4

我在想,爲什麼不這項工作:模式匹配不起作用

def example(list: List[Int]) = list match { 
    case Nil => println("Nil") 
    case List(x) => println(x) 
    }            

    example(List(11, 3, -5, 5, 889, 955, 1024)) 

它說:

scala.MatchError: List(11, 3, -5, 5, 889, 955, 1024) (of class scala.collection.immutable.$colon$colon) 

回答

15

它不起作用,因爲List(x)意味着只有一個元素的列表。檢查它:

def example(list: List[Int]) = list match { 
    case Nil => println("Nil") 
    case List(x) => println("one element: " + x) 
    case xs => println("more elements: " + xs) 
} 

example(List(11, 3, -5, 5, 889, 955, 1024)) 
//more elements: List(11, 3, -5, 5, 889, 955, 1024) 
example(List(5)) 
//one element: 5 
+0

XS可以是任何類型的。我如何正確捕獲List [Int]類型的xs? –

+2

這是scala常見的問題,有用的鏈接:http://stackoverflow.com/questions/12218641/scala-2-10-what-is-a-typetag-and-how-do-i-use-it – Infinity

6

因爲List(x)只與一個元素相匹配的列表。所以

def example(list: List[Int]) = list match { 
    case Nil => println("Nil") 
    case List(x) => println(x) 
} 

只適用於零或一個元素的列表。

2

正如其他海報指出,List(x)只匹配1個元素的列表。

然而,有匹配多個元素的語法:

def example(list: List[Int]) = list match { 
    case Nil => println("Nil") 
    case List(x @ _*) => println(x) 
}            

example(List(11, 3, -5, 5, 889, 955, 1024)) // Prints List(11, 3, -5, 5, 889, 955, 1024) 

這是有趣@ _*東西,它使不同。 _*與重複的參數匹配,並且x @說「將其綁定到x」。

與任何可匹配重複元素的模式匹配(例如,Array(x @ _*)Seq(x @ _*))相同。 List(x @ _*)也可以匹配空列表,雖然在這種情況下,我們已經匹配了零。

您還可以使用_*匹配「休息」,如:

def example(list: List[Int]) = list match { 
    case Nil => println("Nil") 
    case List(x) => println(x) 
    case List(x, xs @ _*) => println(x + " and then " + xs) 
} 
+0

什麼(x :: xs)? –

+0

@Grienders你能否詳細說明一下?你想知道什麼(x :: xs)? –