How should I remove the first occurrence of an object from a list in Scala?

前端 未结 2 949
再見小時候
再見小時候 2021-01-13 16:56

What is the best way to remove the first occurrence of an object from a list in Scala?

Coming from Java, I\'m accustomed to having a List.remove(Object o) method tha

相关标签:
2条回答
  • 2021-01-13 17:41

    This is a case where a little bit of mutability goes a long way:

    def withoutFirst[A](xs: List[A])(p: A => Boolean) = {
      var found = false
      xs.filter(x => found || !p(x) || { found=true; false })
    }
    

    This is easily generalized to dropping the first n items matching the predicate. (i<1 || { i = i-1; false })

    You can also write the filter yourself, though at this point you're almost certainly better off using span since this version will overflow the stack if the list is long:

    def withoutFirst[A](xs: List[A])(p: A => Boolean): List[A] = xs match {
      case x :: rest => if (p(x)) rest else x :: withoutFirst(rest)(p)
      case _ => Nil
    }
    

    and anything else is more complicated than span without any clear benefits.

    0 讨论(0)
  • 2021-01-13 17:52

    You can clean up the code a bit with span.

    scala> def removeFirst[T](list: List[T])(pred: (T) => Boolean): List[T] = {
         |   val (before, atAndAfter) = list span (x => !pred(x))
         |   before ::: atAndAfter.drop(1)
         | }
    removeFirst: [T](list: List[T])(pred: T => Boolean)List[T]
    
    scala> removeFirst(List(1, 2, 3, 4, 3, 4)) { _ == 3 }
    res1: List[Int] = List(1, 2, 4, 3, 4)
    

    The Scala Collections API overview is a great place to learn about some of the lesser known methods.

    0 讨论(0)
提交回复
热议问题