この関数の目的は何ですか? どのようなシナリオで使用する必要がありますか?
引数を取る関数が必要なコンテキストで使用しますが、実際には引数を気にせず、毎回同じ値を返したいだけです。些細な例はList.map (const 42) xs
、n 個のアイテムのリストを n 個の 42 のリストに変換する です。
あまりばかげていない (しかしより抽象的な) 例は、値を生成するために何かを行う関数ですが、特定の (たとえば、何かが成功しなかった場合) 条件下では、代わりにユーザー提供の関数を呼び出して、値を与える代わりに値を生成します。引数としての状況に関する情報。状況によっては、情報を気にせず、毎回同じデフォルト値を返すだけなので、const
ここで機能します。
() を入れる理由; 最初?
生成されたコードだけでなく、その内部表現においても、OCaml コンパイラは実際には多引数関数を持っています。let f x y = ...
orのような関数を定義するとlet f x = fun y -> ...
、OCaml は実際にこれを (別の関数を返す 1 引数の関数ではなく) 2 引数の関数に変換します。したがって、それf 1 2
を呼び出す場合、それは 2 つの引数の関数への単純な呼び出しであり、代替手段よりもはるかに効率的です。ただし、単に実行f x
すると、クロージャーを作成するためにいくつかの追加コードが生成されます。これは、クロージャーを直接返すよりも効率的ではありません。
したがって、この最適化により、すべての引数を指定して関数を呼び出すとパフォーマンスが向上しますが、そうでない場合は実際には非生産的です。前に を追加する()
と、最適化が無効になります (関数の形式がなくなったためf x = fun y -> ...
)。は 1 つの引数だけで呼び出されることを意図しているためconst
( を直接呼び出しconst x y
ても意味がないので、 を記述しても問題ありませんx
)、これによりパフォーマンスが向上します。
let const c = fun () -> c と書いてみませんか? これにより、ユニットをパラメーターとして受け取る関数が与えられ、常に初期 c が返されます。
unit
その場合、関数は、関数の取得が予想されるコンテキストでのみ機能するため、これは非常に少数のケースです。たとえば、がユニットのリストであるList.map (const 42) xs
場合にのみ機能しますxs
が、これはほぼ確実ではありません。