Scala隐含参数

时间:2014-11-26 00:39:38

标签: scala monads typeclass

好的,我终于设法理解了函数参数中隐含的用例,并使我的类型类工作。我们来看看我的monad类型:

trait Monad[M[_]] extends Functor[M] { self =>
  def pure[a](value: a): M[a]

  def flatMap[a, b](ma: M[a])(f: a => M[b]): M[b]
}

我为我的解析器monad创建了一个类型类实例(现在只是一个假人):

case class Parser[a](value: (Unit => a)) {
  def >>=[b](f: a => Parser[b])(implicit p: Monad[Parser]): Parser[b] =
    p.flatMap(this)(f)

  def fmap[b](f: a => Parser[b])(implicit p: Monad[Parser]): Parser[b] =
    p.map(this)(f)
}

object Parser {
  implicit object MonadInstance extends Monad[Parser] {
    override def pure[a](value: a): Parser[a] =
      new Parser[a]({ _ => value })

    override def flatMap[a, b](ma: Parser[a])(f: (a) => Parser[b]): Parser[b] =
      f(ma.value())

    override def map[a, b](fa: Parser[a])(f: (a) => b): Parser[b] =
      new Parser[b]({ _ => f(fa.value()) })
  }
}

我只是想知道,如果我可以使用monad实例而不必在我使用monad的任何地方声明隐式参数。有没有办法在全球范围内“导入”这个功能?

1 个答案:

答案 0 :(得分:0)

Predef中有一个隐式调用的方法,专为此用例设计:

def implicitly[T](implicit t: T):T = t

可以这样使用:

val mParser = implicitly[Monad[Parser]]

原件:

在scala中,会在相关类型的伴随对象中自动查找implicits。因此隐含地[Monad [Parser]]应该工作,因为它应该在对象Parser中查找。

请注意,由于解释器的工作方式,在repl中定义伴随对象有点痛苦。最简单的方法是将它们包装在一个对象中,或者不在新行上启动对象Parser(仅用于repl)。