is there cleaner way, i.e. without nested for expressions, write following f, g, , doit functions?
import scala.concurrent.future import scala.concurrent.executioncontext.implicits.global def f(x: int): future[either[string, int]] = future(right(100)) def g(x: either[string, int], y: int): future[either[string, int]] = future { x match { case right(i) => right(i + y) case left(err) => left(err) }} def doit: future[either[string, int]] = { x <- { <- f(100) } yield y <- { <- g(x, 25) } yield } yield y i'm speculating use monad transformers, don't understand them.
if you're working types foo[qux[a]] both foo , qux monads , find you're writing lot of nested for-comprehensions, first thing should check scalaz (or cats) quxt monad transformer. allow work quxt[foo, a] values monadically single level of fors.
as other answers point out, don't need nested for-comprehensions in case given definition of g. i'm going assume want work values way inside future[either[string, ?]], without noisy g method, in case want eithert[future, string, int]:
import scalaz._, scalaz._ import scala.concurrent.future import scala.concurrent.executioncontext.implicits.global def f(x: int): eithert[future, string, int] = eithert.fromeither(future[either[string, int]](right(100))) // or just: // def f(x: int): eithert[future, string, int] = eithert.right(future(100)) def doit: eithert[future, string, int] = f(100).map(_ + 25) eventually you'd write doit.run future[either[string, int]]:
scala> doit.run.onsuccess { case e => println(e) } \/-(125) which same result implementation gives (except we've got scalaz's disjunction type).
Comments
Post a Comment