Scala中removeN方法抛出java.util.NoSuchElementException的解决方法
解决Scala列表移除指定元素n次出现时的NoSuchElementException错误
问题场景
实现移除列表中指定元素的n次出现(非全部),但调用removeN(List(1,2,3,2,1), 0, 2)时抛出java.util.NoSuchElementException,期望返回原列表。
原代码
def removeN[A](xs: List[A], elem: A, n: Int) : List[A] = { val elemCount = xs.groupBy(identity).mapValues(_.size)(elem) if (xs.contains(elem) == false) xs else if (elemCount == n) xs.filterNot(x => x == elem) else { val (left, right) = xs.span(_ != elem) print(s"$left and $right") left ::: right.tail } }
错误原因
代码第一行直接通过(elem)访问groupBy生成的Map键值对,当elem不在列表中时,Map不存在该键,直接抛出NoSuchElementException。尽管后续有xs.contains(elem)的判断,但这行代码在判断前就已执行,导致异常提前触发。此外,原代码仅实现了移除1次元素的逻辑,未完成移除n次的需求。
修复后的代码
def removeN[A](xs: List[A], elem: A, n: Int): List[A] = { // 递归辅助函数,处理逐元素移除逻辑 def removeHelper(remaining: List[A], count: Int): List[A] = remaining match { case Nil => Nil // 遇到目标元素且还需移除时,跳过当前元素,剩余移除次数减1 case head :: tail if head == elem && count > 0 => removeHelper(tail, count - 1) // 非目标元素或已无需移除时,保留当前元素继续处理后续列表 case head :: tail => head :: removeHelper(tail, count) } // 实际移除次数不能超过列表中目标元素的总数量 val actualRemove = math.min(n, xs.count(_ == elem)) removeHelper(xs, actualRemove) }
测试验证
removeN(List(1,2,3,2,1), 0, 2)→List(1, 2, 3, 2, 1)(符合预期,元素0不存在,直接返回原列表)removeN(List(1,2,3,2,1), 2, 1)→List(1, 3, 2, 1)(移除1次元素2)removeN(List(1,2,3,2,1), 2, 2)→List(1, 3, 1)(移除2次元素2)
内容的提问来源于stack exchange,提问作者Jae
相关产品推荐
相关产品推荐

