簡體   English   中英

Scala本地類型推斷下划線表示法

[英]Scala local type inference underscore notation

通過研究“ Scala中的函數式編程”,我想知道為什么以下代碼會給出缺少的參數類型錯誤。

定義了以下樹數據結構:

sealed trait Tree[+A]
case class Leaf[A](value: A) extends Tree[A]
case class Branch[A](left: Tree[A], right: Tree[A]) extends Tree[A]

以及以下方法:

object Tree {

  def fold[A,B](t: Tree[A])(z: A => B)(f: (B,B) => B): B = t match {
    case Leaf(v) => z(v)
    case Branch(l,r) => f(fold(l)(z)(f), fold(r)(z)(f))   }

  def size2[A](t: Tree[A]): Int = fold(t)((_) => 1)(_ + _ + 1)

  def maximum2(t: Tree[Int]): Int = fold(t)((a) => a)(_ max _)

  def depth2[A](t: Tree[A]): Int = fold(t)((_) => 0)(1 + (_ max _))

}

該方法size2個maximum2編譯就好了,但深度2不意味着在最后一個函數的類型。

編寫方法如下:

def depth2[A](t: Tree[A]): Int = fold(t)((_) => 0)((a,b) => 1 + (a max b))

使它編譯就好了。

問:為什么Scala不能在帶下划線符號的第一種方法上推斷類型,而在第二種方法上有推斷呢? 是什么使其他方法可以正常編譯?

謝謝你的幫助。

標尺版本:2.11.4

1 + (_ max _)擴展為1 + ((a, b) => a max b) ,這會向1添加一個函數。如果指定類型,則會出現另一個錯誤:

<console>:22: error: overloaded method value + with alternatives:
(x: Double)Double <and>
(x: Float)Float <and>
(x: Long)Long <and>
(x: Int)Int <and>
(x: Char)Int <and>
(x: Short)Int <and>
(x: Byte)Int <and>
(x: String)String
cannot be applied to ((Int, Int) => Int)
           def depth2[A](t: Tree[A]): Int = fold(t)((_) => 0)(1 + ((_: Int) max (_: Int)))

如您所見,您需要明確地放置參數

(a,b) => 1 + (a max b)

或跳過原諒

1 + _ max _

您實際上無法在此處執行此操作,因為它可以像您說的那樣工作

(a,b) => (1 + a) max b

原來,在第一個方法中刪除括號,刪除所有編譯錯誤,如下所示:

def depth2[A](t: Tree[A]): Int = fold(t)((_) => 0)((a,b) => 1 + a max b)

因此,下划線符號似乎總是選擇最接近的范圍來推斷類型。

暫無
暫無

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

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