Scala中List [Try [String]]的分区

时间:2016-10-14 12:05:54

标签: scala

我有# replace the second column for the cumsum of the initial second column data[, 2] <- cumsum(data[, 2]) List个,我需要按TryFailure进行分区,如下所示:

Success

是否已有功能实现此目的? (而不是调用丑陋的import scala.util.{Try, Success, Failure} val list = List(Success(10), Success(20), Failure(new Exception("error1")), Success(30)) val (listTryFailures: List[Try[Int]], listTrySuccesses: List[Try[Int]]) = list.partition(_.isFailure) listTryFailures: List[Try[Int]] = List(Failure(java.lang.Exception: error1)) listTrySuccesses: List[Try[Int]] = List(Success(10), Success(20), Success(30)) val (listFailures: List[Throwable], listSuccesses: List[Int]) = (listTryFailures.map(_.failed.get), listTrySuccesses.map(_.get)) listFailures: List[Throwable] = List(java.lang.Exception: error1) listSuccesses: List[Int] = List(10, 20, 30) + partition(_.isFailure) + map(_.failed.get))?

ps:另一种选择如下:

map(_.get)

但我问的是标准库中是否已存在val listFailures: List[Throwable] = list.collect { case Failure(f) => f } val listSuccesses: List[String] = list.collect { case Success(entry) => entry } // or val listFailures: List[Throwable] = list.flatMap(_.failed.toOption) val listSuccesses: List[String] = list.flatMap(_.toOption) (或类似名称)功能:

partitionSuccess

3 个答案:

答案 0 :(得分:3)

为了完整起见,scalaz版本全部使用import scalaz._, Scalaz._

scala> val l = List(-\/("foo"), -\/("bar"), \/-(2), \/-(4))
l: List[scalaz.\/[String,Int]] = List(-\/(foo), -\/(bar), \/-(2), \/-(4))

scala> l.separate
res7: (List[String], List[Int]) = (List(foo, bar),List(2, 4))

也适用于stdlib Try

scala>     val list = List(Success(10), Success(20), Failure(new Exception("error1")), Success(30))
list: List[scalaz.Validation[Exception,Int]] = List(Success(10), Success(20), Failure(java.lang.Exception: error1), Success(30))

scala> list.separate
res8: (List[Exception], List[Int]) = (List(java.lang.Exception: error1),List(10, 20, 30))

感谢@dibblego

答案 1 :(得分:1)

Scala 2.13开始,现在大多数集合都提供了partitionMap方法,该方法根据返回RightLeft的函数对元素进行分区。

在我们的例子中,我们可以使用将partitionMap转换为Try的函数来调用Either,以便将Success分为Right和{ {1}}和Failure一样:

Left

答案 2 :(得分:0)

正如@Sarveh指出的那样,每BucketName = @"http://s3-eu-west-1.amazonaws.com/bucketName/"没有任何具体的方法。但是自己写一个不应该太难:

List[Try[T]]

现在:

implicit class ListOps[T](val l: List[Try[T]]) extends AnyVal {
  def partitionSuccess(): (List[Throwable], List[T]) = {
    l.foldLeft((List.empty[Throwable], List.empty[T])) {
      (x: (List[Throwable], List[T]), y: Try[T]) => {
        y match {
          case Failure(e) => (e +: x._1, x._2)
          case Success(t) => (x._1, t +: x._2)
        }
      }
    }
  }
}

收率:

def main(args: Array[String]): Unit = {
  val list = List(Success(10), Success(20), Failure(new Exception("error1")), Success(30))
  val (failure, success) = list.partitionSuccess()

  failure.foreach(println)
  success.foreach(println)
}