2015-01-17 62 views
2

我試圖找出在Scala中聲明函數時defvar/val之間的區別。在Scala中聲明一個使用def或var的函數

說我們有一個功能:

scala> def f(x: Int) = { x * 2 } 
f: (x: Int)Int 

而另一個函數g:

scala> var g = (x:Int) => x*2 
g: Int => Int = <function1> 

顯然,他們是通過以下方式相同:

scala> f(2) 
res0: Int = 4 

scala> g(2) 
res1: Int = 4 

不過,我可以做

g = f 
g: Int => Int = <function1> 

但不

scala> f = g 
<console>:13: error: missing arguments for method f; 
follow this method with `_' if you want to treat it as a partially applied function 
val $ires6 = f 
      ^
<console>:10: error: reassignment to val 
     f = g 
     ^

問題1:爲什麼會發生這種情況? 我猜def映射到val

問題2:如果我在聲明使用VAL而不是VAR,他們是等價?如果不是,那麼有什麼區別?

我再試試:

scala> def three(timetwo:(Int) => Int) = { timetwo(3) } 
three: (timetwo: Int => Int)Int 

scala> three(g) 
res47: Int = 6 

scala> three(f) 
res48: Int = 6 

問題3:意思(x: Int)Int是一樣的Int => Int = <function1>?如果是這樣,有什麼情況我們應該相互贊成?

事情是越來越有線與_(下劃線),

scala> three(f _) 
res49: Int = 6 

scala> three(g _) 
<console>:11: error: type mismatch; 
found :() => Int => Int 
required: Int => Int 
      three(g _) 
       ^

問題4:爲什麼會發生這種情況? Scala中_(下劃線)的用法是什麼?

+0

[Scala中定義函數的兩種方式可能的重複。有什麼區別?](http://stackoverflow.com/questions/5009411/two-ways-of-defining-functions-in-scala-what-is-the-difference) –

+0

http://stackoverflow.com/問題/ 2529184 /差之間-方法和 - 功能合階 – Maxim

回答

6

爲什麼會發生這種情況?我猜這個def映射到val。

def是一種方法(使用JVM術語),因此分配它是沒有意義的。

解析器是那麼迷茫,它最終試圖通過解釋分配f = g作爲

val $ires6 = f 
f = g 

兩個語句是非法保存一天,讓你獲得兩個錯誤:

  • 你可以」 t將方法分配給val而沒有顯式類型註釋或_擴展 - 請參閱下文)
  • 您無法重新指定val(如果您想知道, $ires6是一個新鮮val由REPL引入)

,如果我在申報g使用VAL,而不是無功,他們是等價?如果不是,那麼有什麼區別?

不同的是,val不能被重新分配(即它是一個恆定的基準),而var能(即它是一個可變引用)。

更多關於所述對象的位置:What is the difference between a var and val definition in Scala?

意思(X:智力)INT是相同INT => INT =?如果是這樣,有什麼情況我們應該相互贊成?

Methods and functions are not the same,儘管編譯器通過名爲eta-expansion的轉換盡最大努力使你相信它們是。在某些情況下,這種轉換可以自動執行,而在其他情況下,您需要明確並以尾隨_觸發它。

在您的具體示例中(通過預期功能的方法),可以自動執行擴展。

您可以閱讀this Q/A以瞭解更喜歡哪種風格的更深入的討論。

爲什麼會發生這種情況? Scala中_(下劃線)的用法是什麼?

下劃線(_has many uses in scala,其中之一是我以前提到的,即觸發ETA膨脹的方法的成一個函數。

這是一種特殊的方法語法,所以你根本無法將它應用於函數,因爲它沒有任何意義。

這就是爲什麼你可以做f _(這將會把f方法到一個函數),但你不能做g _(因爲g它已經是一個功能)。

相關問題