簡體   English   中英

使用函數文字輸入推理

[英]Type inference with function literals

我正在嘗試解決一些Scala問題集 ,以便用該語言來了解。 我遇到問題11,我的解決方案無法編譯。 我的問題是:為什么Scala中這是非法的?

def countPackSingle[A](list: List[A]): List[Any] = {
  pack(list) map {ls => {
    case head :: Nil => head
    case head :: tail => List(tail.size + 1, head)
  }}
}

IntelliJ很高興這個定義,但編譯器抱怨:

缺少擴展函數的參數類型
必須完全知道匿名函數的參數類型。 (SLS 8.5)

預期的類型是:?

 pack(list) map {ls => { ^ 

我真的沒有得到這條消息試圖告訴我的內容。 scala編譯器可以不推斷ls的類型嗎? 當我通過ls: List[A]指定類型時,問題仍然存在。

在這種情況下:為什么我可以在使用花括號{ }時指定參數ls的類型,而不是在使用parenthesises ( ) 直到今天,我正在尋找一個很好的資源來解釋Scala的不同之處。 到目前為止,我認為在使用文字通過`case和其他一些罕見的場合創建parial函數時 ,它只會產生真正的不同

感謝幫助!

這個結構:

{
  case head :: Nil => head
  case head :: tail => List(tail.size + 1, head)
}

是一個部分函數的語法糖,這就是為什么編譯器會拋出這個消息,scalac認為你正在嘗試創建一個PartilFunction[List[A], List[A]] 要解決此問題,您有三種方法:

1)完成此模式匹配構造:

pack(list) map { ls => ls match {
    case head :: Nil => head
    case head :: tail => List(tail.size + 1, head)
  }
}

2)使用下划線語法:

pack(list) map { _ match {
    case head :: Nil => head
    case head :: tail => List(tail.size + 1, head)
  }
}

這實際上是一樣的。 現在,如果你願意,你可以為ls歸類一個類型,但是scala可以成功地推斷它。

3)使用內聯語法:

pack(list) map {
  case head :: Nil => head
  case head :: tail => List(tail.size + 1, head)
}

這是可能的,因為PartialFunctionFunction的子類,因此可以直接使用partial函數而不是plain函數。

你在結果類型List[Any]沒有任何意義。 1)這種類型不好,導致你丟失所有的類型信息和2)你的功能不是tailrecursive,所以你可以刪除它,讓scalac推斷它為你

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM