2015-11-07 71 views
2

我在阿卡發現了一些奇怪的行爲。當我匹配的模式,我無法添加消息到列表:如何在匹配類型列表中使用模式匹配結果?

var msgs: List[Message] = Message() :: Nil 

    ... 

    override def receive: Receive = { 
    case msg @ Message => { 
     msgs = msgs.::(Message()) // ok 
     //msgs = msgs.::(msg)  // doesn't work 
     sender ! "Thanks!" 
    } 
    case Request => { sender ! msgs.head } 
    case _  => 
    } 

這是ScalaAkka一個錯誤?

爲了修正它,我需要區分類型

msgs = msgs.::(msg.asInstanceOf[Message]) 

這是不方便的解決方案。

回答

4

問題在於您在case語句中發生匹配時發生了細微的錯誤。您在那裏與Message伴隨對象匹配,而不是Message案例類。

看它的另一種方式是,case x @ Y語法可以的話說,「匹配Y類型的任何實例,然後運行的val x: Y = <incoming value>.asInstanceOf[Y]相當於」被認爲是,但在這裏,您提供的推斷類型是一個參數稱爲Message,編譯器需要爲object Message,而不是case class Message()

因此,要修復該行,請寫入參數列表。例如,如果Message類被定義爲:

case class Message() 

這將是:

case msg @ Message() => ... 

相反,如果我們有,說:

case class Message(text: String, id: Int) 

那麼case語句變成像:

case msg @ Message(txt, is) => ... 

或者,如果我們不關心(或者需要使用)的textid參數:

case msg @ Message(_, _) => ... 

對於這裏發生了什麼的稍微技術上更正確的描述,case語句實際上是試圖用火柴隨播對象中的任何「不適用」方法(也稱爲「提取器」)。默認情況下,對於與case類構造函數中提供的參數列表完全匹配的任何case類,伴隨對象中將免費提供applyunapply方法。在上述Message類的第二個版本,相關unapply方法有這樣的簽名:

def unapply(text: String, id: Int): Option[Message] 

你可以閱讀更多關於提取herehere

+0

哦,當然。對不起,這個問題。 – Finkelson