Scala:过滤一组选项

时间:2011-09-28 07:48:59

标签: scala map filter option

假设我有一个函数检查某个操作是否适用于A的实例,如果是,则返回B或None的实例:

   def checker[A,B]( a: A ) : Option[B] = ...

现在我想形成一个包含B的所有有效实例的新集合,删除None值。以下代码似乎可以完成这项工作,但肯定有更好的方法:

   val as = List[A]( a1, a2, a3, ... )
   val bs = 
     as
     .map( (a) => checker(a) )    // List[A] => List[Option[B]]
     .filter( _.isDefined )       // List[Option[B]] => List[Option[B]]
     .map( _.get )                // List[Option[B]] => List[B]

谢谢!

2 个答案:

答案 0 :(得分:25)

这应该这样做:

val bs = as.flatMap(checker)

答案 1 :(得分:11)

上面的答案是正确的,但如果您可以重写checker,建议您使用PartialFunctioncollect。 PartialFunction是类型A => B的函数,不需要为A的所有值定义。这是一个简单的例子:

scala> List(1, 2, 3, 4, "5") collect {case x : Int => x + 42}
res1: List[Int] = List(43, 44, 45, 46)

collect将PartialFunction的实例作为参数,并将其应用于集合的所有元素。在我们的例子中,该函数仅针对Ints定义,并且"5"被过滤。因此,collectmapfilter的组合,这正是您的情况。