18

それはScalaDocにありますが、多くのドキュメントはありません。常に最初のパラメータを返すようです。

Function.const(1)(2)たとえば、を返します1

なぜそれが存在し、なぜそれが有用なのですか?

4

2 に答える 2

29

高階関数に引数として渡すのに便利です。たとえば、リストのすべての要素を同じ要素に置き換えるには:

scala> List(1, 2, 3, 4, 5).map(Function.const(7))
res1: List[Int] = List(7, 7, 7, 7, 7)

もちろん、書くこともできます

scala> List(1, 2, 3, 4, 5).map(_ => 7)
res2: List[Int] = List(7, 7, 7, 7, 7)

コンテキストによっては、一方が他方よりも読みやすい場合があります。

于 2011-05-08T00:42:13.723 に答える
20

より理論的な答えを出すには: const はSKI 微積分の K コンビネータです。「作業する」ことがあまりない非常に抽象的な概念を扱うときに、時々ポップアップします。(Haskell スタイルの) Functor トレイトを考えてみましょう:

trait Functor[F[_]] {
   def fmap[A,B](f:A=>B, fa: F[A]):F[B]
   //(<$) in Haskell
   def left[A,B](a:A, fb:F[B]):F[A] 
}

fmap はファンクタの本質であるため、抽象化する必要があります。しかし、左の一般的な実装を書くことができ、ここでは const が必要です:

trait Functor[F[_]] {
   def fmap[A,B](f:A=>B, fa: F[A]):F[B]
   //(<$) in Haskell
   def left[A,B](a:A, fb:F[B]):F[A] = 
     fmap(Function.const(a), fb)
}

オプションでテスト:

case object OptionFunctor extends Functor[Option] {
   def fmap[A,B] (f:A=>B, fa:Option[A]):Option[B] = fa match {
      case Some(a) => Some(f(a))
      case None => None
   }
}

//left works:
OptionFunctor.left("test",Some(42))
//--> Option[java.lang.String] = Some(test)
OptionFunctor.left("test",None:Option[Int])
//--> Option[java.lang.String] = None

ご覧のとおり、 left は本来あるべきことを行います (2 番目の引数でこのファンクターの「ロール モデル」または「パターン」が既にある場合に、何らかのファンクターで値をラップします)。ファンクターの種類について何も知らずに非常に抽象的に定義することは、const を使用することによってのみ可能でした。

于 2011-05-08T08:11:53.270 に答える