第一級関数
Scala において、関数は第一級関数 first-class function です。第一級関数なので、関数を値の様にして扱うことができます。例えば以下のように関数を f という値として定義できます。
val f:Int=>Int = x=>x*x println(f(3))
結果は 9 が出力されます。
上記は以下と同じ意味になります。
val f:Function[Int, Int] = x=>x*x println(f.apply(3))
f(3) の呼び出しは実際には Function 型の apply メソッドの呼び出しでしかないのです。
さらに以下に書き換えることができます。
val f:Function[Int, Int] = new Function[Int, Int]{ def apply(x:Int):Int = x*x } println(f.apply(3))
Function の無名クラス定義にて apply メソッドを定義しています。
さらに冗長に書いてみると以下とも同じ意味です。
class Square extends Function[Int,Int] { def apply(x:Int):Int = x*x } val f:Function[Int, Int] = new Square println(f.apply(3))
ということで、関数は Function のインスタンスの apply メソッドを定義しているというわけです。
Scalaのライブラリの中を見ると
Function[Int, Int] が何を意味するかというと、Predef にて以下の定義となっています。
type Function[-A, +B] = Function1[A, B]
Function は Function1 の型エイリアスとなっています。
そして、Function1 は、
trait Function1[-T1, +R] extends AnyRef { self => def apply(v1:T1): R ・・・
のような trait となっています。T1 を引数にとり、R を結果型として返す apply 関数が定義されていますね。
つまり、
Int=>Int
と
Function1[Int, Int]
は同じ意味となります。
また、
x=>x*x
は
def apply(x:Int):Int = x*x
のメソッドを定義していることになります。