吴师兄学算法day06 双指针 26. 删除有序数组中的重复项
题目:26. 删除有序数组中的重复项
易错点:
- 为什么不可以写大于nums[slow]
- 因为会出现多个[0,1,2,2,...]情况
- 为什么返回slow的值?
- slow最后是5正好是移动后数组里的长度
代码示例:
from typing import List
class Solution:
def removeDuplicates(self, nums: List[int]) -> int:
if len(nums) == 1:
return 1
fast = 1
slow = 1
while fast < len(nums):
if nums[fast] > nums[fast-1]: # 要写fast-1 # ???为什么不能写nums[fast] > nums[slow]
# 因为会出现 # [0,1,2,1,1,2,2,3,3,4] 当slow=3 nums[slow]=1;此时fast=6时,nums[fast]=2 移动后变为[0,1,2,2,1...]
# 可以在这个位置debug
nums[slow] = nums[fast]
fast += 1
slow += 1
else: # 不大于就只移动快指针
fast += 1
return slow
if __name__ == '__main__':
obj = Solution()
nums = [0, 0, 1, 1, 1, 2, 2, 3, 3, 4]
out = obj.removeDuplicates(nums)
print(out)
扩展写法:
赋值来写:
class Solution:
def removeDuplicates(self, nums: List[int]) -> int:
fast = 0
slow = 0
while fast< len(nums):
if fast == 0 or nums[fast] !=nums[fast-1]:# 首位置赋值,后续位置只有不相等(就是大于的)就赋值
nums[slow] = nums[fast]
slow +=1
fast +=1
else:
fast +=1
return slow
扩展写法2:continue跳过重复的
-
这里要理解这个left指针的含义,是保存已经处理过的值。因为默认就已经把0位置的保留了,
""" 关键在于 理解指针left的含义及其如何移动。 在您的代码中,left指针表示的是已处理区间的最后一个元素的索引。这个区间是不包含任何重复元素的。 每当我们在right指针处遇到一个新的非重复元素(即nums[right] != nums[left]), 我们将要做的是先将left增加1(以扩展不重复区间的大小),然后将right处的新元素赋值到left处。 """
class Solution:
def removeDuplicates(self, nums: List[int]) -> int:
left = 0
for right in range(len(nums)):
# 如果相等, 说明right指向的元素是重复元素,不保留
if nums[right] == nums[left]:
continue
# 如果不相等, 说明right指向的元素不是重复元素,保留,然后右移left一个单位,再把right的值赋给left
left += 1
nums[left] = nums[right]
return left + 1
作者:Eason
链接:https://leetcode.cn/problems/remove-duplicates-from-sorted-array-ii/solutions/886423/yi-zhao-miao-sha-suo-you-tong-lei-xing-t-ws3g/
来源:力扣(LeetCode)
著作权归作者所有。商业转载请联系作者获得授权,非商业转载请注明出处。
扩展写法3:
- 这种写法可以跟80题对上
class Solution:
def removeDuplicates(self, nums: List[int]) -> int:
slow = 0
for fast in range(len(nums)):
if slow < 1 or nums[fast] != nums[slow-1]:
nums[slow] = nums[fast]
slow +=1
return slow
总结:
- 其实我可以写出来的。
- 再听一听老师讲的。
- 吴师兄讲的一般。。。
参考:
https://ahym1n4sq5.feishu.cn/docx/AQwAd0mWdoz7UtxSqNAc7K9tnaf
Eason 思路不错 链接