总结两个选项

Jen*_*olm 8 scala option scala-collections

假设我有两个可选的Ints(都可以是Some或None):

val one : Option[Int] = Some(1)
val two : Option[Int] = Some(2)
Run Code Online (Sandbox Code Playgroud)

我的问题如下:有没有任何聪明的方法来使用Scalas精彩的收集方法来总结它们?我意识到我可以将它们合并到一个集合中,flatten并使用reduceLeftOption如下:

(one :: two :: Nil).flatten.reduceLeftOption(_ + _)     // Some(3)
Run Code Online (Sandbox Code Playgroud)

但是,上述解决方案意味着创建一个新的集合,并生活在一个富裕和发达的世界,从我可能沉浸其中的所有其他第一世界活动中抽出时间.对于像我们这样的程序员来说编程越来越奢侈的世界,必须有一个或多个豪华的第一世界答案,对吗?

编辑:所以要拼出来,这里有一些例子:

如果one = Some(1),two = Some(2)我们应该有一些(3)

如果one = Some(1),two = None我们应该有一些(1)

如果one = None,two = Some(2)我们应该有一些(2)

如果这两个onetwoNone 我们应该没有,因为无论是onetwo可以正确求和.

希望澄清的事情:-)

Rég*_*les 18

for (x <-one; y <- two) yield x+y
Run Code Online (Sandbox Code Playgroud)

或者可读性较差但严格等同:

one.flatMap{x=>two.map(x+_)}
Run Code Online (Sandbox Code Playgroud)

更新:由于您的最新编辑非常明确,因此您只需要None输入选项时的结果None.在这种情况下,我不认为你在简单性方面会比你已经使用的更好.我可以缩短一点但总体来说这是相同的:

(one ++ two).reduceOption(_ + _)
Run Code Online (Sandbox Code Playgroud)


ste*_*tew 14

强制性scalaz答案是使用scalaz选项monoid:

scala> one |+| two
res0: Option[Int] = Some(3)
Run Code Online (Sandbox Code Playgroud)

对于None,它会做你想要的事情:

scala> two |+| None
res1: Option[Int] = Some(2)

scala> none[Int] |+| none[Int]
res2: Option[Int] = None
Run Code Online (Sandbox Code Playgroud)

没有方法是scalaz的一个方法,它有助于类型推断,因为而不是返回None <: Option[Nothing]它返回a Option[Int],有一个类似的方法来自Some,它为任何给定的A而不是Some [A]返回一个Option [A]:

scala> 1.some |+| 2.some
res3: Option[Int] = Some(3)
Run Code Online (Sandbox Code Playgroud)

  • 去做就对了!scalaz是我添加到任何项目的第一个库.一旦你开始习惯它,你会发现那里有大量的宝石你不想没有:) (2认同)
  • 这是一个很好的介绍视频,从我们自己的@oxbow_lakes的monoids开始:http://skillsmatter.com/podcast/scala/practical-scalaz-2518 (2认同)

gzm*_*zm0 5

怎么样:

one.map(_ + two.getOrElse(0)).orElse(two)
Run Code Online (Sandbox Code Playgroud)