Question

Im wondering if there is a short hand for collapsing a map of an option. For example

def divideByThree(x:Int) = if (x == 0) None else Some(x/3)

val result = Some(6) map (divideByThree(_))
resut:Option[Option[Int]] = Some(Some(2))

To fix this I do

val result = Some(6) match {
   case Some(i) => divideByThree(i)
   case None    => None
}

Which seems a bit heavy going. I could create an implicit function on Option say mapOption to deal with this, but am wondering if there is a nicer way I haven't thought of.

Was it helpful?

Solution

You can use flatMap like in:

def divideByThree(x:Int) = if (x == 0) None else Some(x/3)

val opx = None // Or: Some(10)
val mapped = opx.flatMap(divideByThree)

println(mapped)

OTHER TIPS

How about flatMap() ? It'll perform the map and then flatten

val result = Some(6) flatMap (divideByThree(_))
result: Option[Int] = Some(2)

Scala has kind of monadic syntax: for comprehension

val div = ( case x if x%3 == 0 => x/3} : PartialFunction[Int,Int] ).lift
val exp = (l : Option[Int]) => for {
             x <- l
             r <- div(x)
           } yield r

test it:

scala> exp(Some(3))
res1: Option[Int] = Some(1)

scala> exp(Some(4))
res2: Option[Int] = None

scala> exp(None)
res3: Option[Int] = None
Licensed under: CC-BY-SA with attribution
Not affiliated with StackOverflow
scroll top