题目描述
给定一个数组 nums 和一个值 val,你需要原地移除所有数值等于 val 的元素,返回移除后数组的新长度。
不要使用额外的数组空间,你必须在原地修改输入数组并在使用 O(1) 额外空间的条件下完成。
元素的顺序可以改变。你不需要考虑数组中超出新长度后面的元素。
解法:快慢指针
代码
先上代码,能看懂就不用看思路了
func removeElement(nums []int, val int) int {
i, j := 0, 0
for ; j < len(nums); j++ {
if nums[j] != val {
nums[i] = nums[j]
i++
}
}
return i
}
思路
- 首先题目给了要求,不使用额外的数组空间,也就是说O(N)是不允许的,最多使用O(1)。从做题的经验来看,大方向上就要往双指针上来考虑了。
- 在确定双指针的前提下,考虑可能会遇到的情况。i, j两个指针,==val或者!=val,要判断的条件非常多,是很容易考虑错的。 这里提供一个思路:
- 进行覆盖而不是进行交换。==val的数据是没有用的,直接用j指针的数据将其覆盖
- j指针的作用是向后扫描!=val的数据
- i指针的作用是将!=val的数据维护在数据的前端。
- i指针前的数据保证!=val,j向后扫描,遇到val跳过,遇到!=val的数据,直接放到i处。
这样来考虑这个问题,就不需要对各个条件进行判断了,代码也很简洁。