如何通过谓词将序列分成两部分?
如何通过谓词将序列分成两个列表?
另类:我可以使用filter
和filterNot
,或者写我自己的方法,但没有一个更好的更一般的(内置)方法?
通过使用partition
方法:
scala> List(1,2,3,4).partition(x => x % 2 == 0) res0: (List[Int], List[Int]) = (List(2, 4),List(1, 3))
好的partition
是你想要的东西 – 还有另一种方法,也使用谓词来分割列表中的两个: span
。
第一个分区将把所有“真”元素放在一个列表中,其他的放在第二个列表中。
span将把所有元素放在一个列表中,直到元素为“false”(就谓词而言)。 从这一点开始,它将把这些元素放在第二个列表中。
scala> Seq(1,2,3,4).span(x => x % 2 == 0) res0: (Seq[Int], Seq[Int]) = (List(),List(1, 2, 3, 4))
你可能想看看scalex.org – 它允许你通过签名来searchscala标准库中的函数。 例如,键入以下内容:
List[A] => (A => Boolean) => (List[A], List[A])
你会看到分区 。
如果你需要一些额外的东西,你也可以使用foldLeft。 我刚写了一些这样的代码,当分区没有削减:
val list:List[Person] = /* get your list */ val (students,teachers) = list.foldLeft(List.empty[Student],List.empty[Teacher]) { case ((acc1, acc2), p) => p match { case s:Student => (s :: acc1, acc2) case t:Teacher => (acc1, t :: acc2) } }
如果你想把一个列表分成两块以上,并且忽略边界,你可以使用类似的方法(如果你需要search整数,可以修改)
def split(list_in: List[String], search: String): List[List[String]] = { def split_helper(accum: List[List[String]], list_in2: List[String], search: String): List[List[String]] = { val (h1, h2) = list_in2.span({x: String => x!= search}) val new_accum = accum :+ h1 if (h2.contains(search)) { return split_helper(new_accum, h2.drop(1), search) } else { return accum } } return split_helper(List(), list_in, search) } // TEST // split(List("a", "b", "c", "d", "c", "a"), {x: String => x != "x"})