映射A =>选项[B]用于As的不可变集合

时间:2014-12-16 15:16:44

标签: scala

Scala的标准库中是否有以下函数的等价物?

def traverse[A, B](collection: List[A])(f: A => Option[B]): Option[List[B]]

traverse应用可能无法访问不可变列表的函数。它在第一次失败时返回None。如果一切正常,它会返回Some(list)

我在这里使用列表,但它可能是不可变的哈希映射,例如。

2 个答案:

答案 0 :(得分:1)

正如评论中提到的那样,scalaz traverseU正是你想要的

  import scalaz._
  import Scalaz._

  val list = List(1, 2, 3, 4)

  println(list.traverseU(i => Option(i+1)))
  println(list.traverseU(i => if (i>2) Option(i+1) else None))

输出:

Some(List(2, 3, 4, 5))
None

<强>更新

使用Map它有点复杂

  val map = Map("a" -> 1, "b" -> 2, "c" -> 3)

 map.toList.traverseU { case (k, v) => Option((k, v+1)) } map (_.toMap)
 map.toList.traverseU { case (k, v) => if (v > 2) Option((k, v)) else None } map (_.toMap)

答案 1 :(得分:0)

您可以traverseU使用scalaz ListMap s:

import scalaz._, Scalaz._

(1 to 3).toList.traverseU{ x => (x > 0) option x }
// Some(List(1, 2, 3))

(1 to 3).toList.traverseU{ x => (x > 1) option x }
// None

import scalaz.std.map._

val m = Map('a -> 1, 'b -> 2, 'c -> 3)

m.traverseU{ x => (x > 1) option x }
// None

m.traverseU{ x => (x > 0) option x }
// Some(Map('a -> 1, 'b -> 2, 'c -> 3))

您还可以将其与indexedSeqsetvector一起使用,并从scalaz.std.<instancesObject>._进行其他导入。

import scalaz.std.indexedSeq._

(1 to 3).traverseU{ _.some }
// Option[IndexedSeq[Int]] = Some(Vector(1, 2, 3))

您还可以实施Traverse以将其与其他馆藏一起使用。