Scala 中 EvalOption[A] 的 Monad 实例

问题描述 投票:0回答:1

想象一个

EvalOption
类型定义如下:

type EvalOption = [A] =>> Eval[Option[A]]

是否有可能以维护 Eval 堆栈安全的方式创建 Monad 实例?

我能够为这种类型创建一个 Applicative 实例,但是我在实现

flatMap
方法时遇到了问题。所以,如果有人知道这样做的方法,我将非常感激😄。

谢谢,祝你玩得愉快!

scala monads scala-cats applicative flatmap
1个回答
0
投票

是的,有可能:

import cats.Monad
import cats.data.Eval
import cats.implicits._

type EvalOption[A] = Eval[Option[A]]

implicit val evalOptionMonad: Monad[EvalOption] = new Monad[EvalOption] {
  def pure[A](x: A): EvalOption[A] = Eval.now(Option(x))

  def flatMap[A, B](fa: EvalOption[A])(f: A => EvalOption[B]): EvalOption[B] =
    Eval.defer {
      fa.flatMap {
        case Some(a) => f(a)
        case None => Eval.now(None)
      }
    }
}

flatMap
方法中,我们将整个计算包装在
Eval.defer
中,这确保了
flatMap
计算不会被急切地评估。这意味着每个
flatMap
操作都被评估为一个单独的
Eval
,从而保持堆栈安全。

© www.soinside.com 2019 - 2024. All rights reserved.