web-dev-qa-db-ja.com

オプションオプションのオプション解除

_val s: Option[Option[String]]_があるとします。したがって、次の値を持つことができます。

Some(Some("foo"))Some(None)None

最初のものがSome("foo")になり、他の2つがNoneになるように減らしたいと思います。明らかにこれを達成する方法はたくさんありますが、私はシンプルで、おそらく組み込みの、1つ未満のライナーを探しています。

40
Knut Arne Vedaa

scalazjoinを使用してこれを行うことができます。これはモナド操作:

doubleOpt.join

ここにそれはREPLにあります:

scala> import scalaz._; import Scalaz._
import scalaz._
import Scalaz._

scala> some(some("X")).join
res0: Option[Java.lang.String] = Some(X)

scala> some(none[String]).join
res1: Option[String] = None

scala> none[Option[String]].join
res3: Option[String] = None

モナドの型クラスインスタンスを持つものなら何でも利用できます。

16
oxbow_lakes
s.flatten

スタックオーバーフローが許す最小限に私を連れて行くためにたくさんの文字が続きます

13
Dave Griffith

Iterableへの変換は問題ないと思います。これらの手順を使用して、Option[Option[String]から単一のOption[String]に移動します

s.flatten.headOption 

(これはOption[String]を返します)

4
Dean Hiller

次のようにflatMapを使用できます。

val options = List(Some(Some(1)), Some(None), None)
options map (_ flatMap (a => a))

これにより、List[Option[Option[Int]]]List[Option[Int]]にマップされます。
オプションがある場合は、次のように使用できます。

val option = Some(Some(2))
val unzippedOption = option flatMap (b => b)

これにより、Option[Option[Int]]Option[Int]にフラット化されます。

1
tgr