文章链接:https://programmercarl.com/数组理论基础.html
题目建议: 大家能把 704 掌握就可以,35.搜索插入位置 和 34. 在排序数组中查找元素的第一个和最后一个位置 ,如果有时间就去看一下,没时间可以先不看,二刷的时候在看。
先把 704写熟练,要熟悉 根据 左闭右开,左闭右闭 两种区间规则 写出来的二分法。
题目链接:https://leetcode.cn/problems/binary-search/
文章讲解:https://programmercarl.com/0704.二分查找.html
视频讲解:https://www.bilibili.com/video/BV1fA4y1o715
时间复杂度:O( l o g 2 n log_2n log2n)
空间复杂度:O(1)
class Solution:
def search(self, nums, target):
left = 0 # 定义target在一个左闭右闭的区间中:[left, right]
right = len(nums) - 1
while left <= right: # 若 right < left,则区间不成立
middle = (left + right) // 2
if target < nums[middle]:
right = middle - 1 # 若target在左区间,则区间变为[left, middle - 1]
elif target > nums[middle]:
left = middle + 1 # 若target在右区间,则区间变为[middle + 1, right]
else:
return middle # 若target等于中间值,则找到目标值,返回下标
return -1 # 未找到目标值
时间复杂度:O( l o g 2 n log_2n log2n)
空间复杂度:O(1)
class Solution:
def search(self, nums, target):
left = 0 # 定义target在一个左闭右开的区间中:[left, right)
right = len(nums)
while left < right: # 若 right <= left,则区间不成立
middle = (left + right) // 2
if target < nums[middle]:
right = middle # 若target在左区间,则区间变为[left, middle)
elif target > nums[middle]:
left = middle + 1 # 若target在右区间,则区间变为[middle + 1, right)
else:
return middle # 若target等于中间值,则找到目标值,返回下标
return -1 # 未找到目标值
题目建议: 暴力的解法,可以锻炼一下我们的代码实现能力,建议先把暴力写法写一遍。 双指针法 是本题的精髓,今日需要掌握,至于拓展题目可以先不看。
题目链接:https://leetcode.cn/problems/remove-element/
文章讲解:https://programmercarl.com/0027.移除元素.html
视频讲解:https://www.bilibili.com/video/BV12A4y1Z7LP
时间复杂度:O( n 2 n^2 n2)
空间复杂度:O(1)
class Solution:
def removeElement(self, nums, val):
i = 0
n = len(nums)
while i < n:
if nums[i] == val:#若相等,则元素前移,数组长度减一
for j in range(i, n-1):
nums[j] = nums[j+1]
n -= 1
else: #若不相等,则指针后移,继续判断
i += 1
return n
作用: 通过一个快指针和慢指针在一个for循环下完成两个for循环的工作
新数组:不含有目标元素的数组
快指针:冲锋陷阵,向前遍历寻找属于新数组的元素,找到就传给慢指针
慢指针:固守后方,指向新数组最后一个元素的下标
时间复杂度:O(n)
空间复杂度:O(1)
class Solution:
def removeElement(self, nums, val):
fast = 0
slow = 0
n = len(nums)
while fast < n:
if nums[fast] != val:
nums[slow] = nums[fast]
slow += 1
fast += 1
return slow
1、i 的值可以在循环体内修改,但它不会影响循环的迭代次数以及下一次迭代时 i 的起始值
for i in range(3):
print(f'初始时i={i}')
i -= 1
print(f'结束时i={i}\\n')
'''
打印结果为:
初始时i=0
结束时i=-1
初始时i=1
结束时i=0
初始时i=2
结束时i=1
'''
2、range() 函数中的参数可以在循环体内修改,但它不会影响循环的迭代次数
n = 3
for i in range(n):
print(f'初始时i={i},n={n}')
n -= 1
print(f'结束时i={i},n={n}\\n')
'''
打印结果为:
初始时i=0,n=3
结束时i=0,n=2
初始时i=1,n=2
结束时i=1,n=1
初始时i=2,n=1
结束时i=2,n=0
'''
总结:for循环事真多,不如all in while循环