【LeetCode算法题】各类基础排序算法的Python实现
【LeetCode算法题】数组经典题目分析
本文对LeetCode中的数组类的经典题目进行分析,题目序号分别为 704.二分查找
,27.移除元素
,977.有序数组的平方
,209.长度最小的子数组
,59.螺旋矩阵ll
Q:给定一个 n 个元素有序的(升序)整型数组 nums 和一个目标值 target ,写一个函数搜索 nums 中的 target,如果目标值存在返回下标,否则返回 -1。
分析:有序数组查询特定值,一般的折半查找思路。
class Solution(object):
def search(self, nums, target):
"""
:type nums: List[int]
:type target: int
:rtype: int
"""
low = 0;
high = (len(nums) - 1);
while (low <= high):
mid = (low + high) // 2;
if (nums[mid] == target):
return mid;
if (nums[mid] < target):
low = mid + 1;
if (nums[mid] > target):
high = mid - 1;
return -1;
Q:给你一个数组 nums 和一个值 val,你需要 原地 移除所有数值等于 val 的元素,并返回移除后数组的新长度。
注:不要使用额外的数组空间,你必须仅使用 O(1) 额外空间并原地修改输入数组。
分析:利用快慢指针的思维,当 fast 所指的值等于 val,仅向后移动 fast ,当 fast 所指的值不等于 val 时 fast 与 slow 均向前移动一位,且将 fast 所指的值赋给 slow 所指的地址。
class Solution(object):
def removeElement(self, nums, val):
"""
:type nums: List[int]
:type val: int
:rtype: int
"""
slow = 0;
fast = 0;
while (fast < len(nums)):
if (nums[fast] != val):
nums[slow] = nums[fast];
slow += 1;
fast += 1;
return slow;
Q:给你一个按 非递减顺序 排序的整数数组 nums,返回 每个数字的平方 组成的新数组,要求也按 非递减顺序 排序。
注:初始整数数组存在负数
分析:基本思路是先将数组元素平方,然后再对数组进行排序,这里的排序可以用各种排序算法,参考:【LeetCode算法题】各类基础排序算法的Python实现。但该思路一般会导致时间超时,可以采用双指针思维,创建一个空数组,仅在数组两头才可能取最大值,建立左右指针 left 与 right,将大的添加到空数组头,并将对应指针向里移一单位,直到指针重合。
class Solution(object):
def sortedSquares(self, nums):
"""
:type nums: List[int]
:rtype: List[int]
"""
low = 0;
high = len(nums) - 1;
nums_ = [];
while (low <= high):
if (nums[low]**2 <= nums[high]**2):
nums_.insert(0, nums[high] ** 2);
high = high - 1;
else:
nums_.insert(0, nums[low] ** 2);
low = low + 1;
return nums_;
Q:给定一个含有 n 个正整数的数组和一个正整数 s ,找出该数组中满足其和 ≥ s 的长度最小的 连续 子数组,并返回其长度。如果不存在符合条件的子数组,返回 0。
分析:基本思路是用两层 for 循环将所有可能的子数组遍历,找到满足条件的最小长度,该方式时间复杂度较高,改进思路是减少循环次数,双循环是同时限制了子数组的起止,单循环仅限制子数组的止。核心思路是:创建两个指针start,end,初始两指针均在数组头,之后推进 end 指针,当出现 sum(array[start, end]) > val 时,停止end后移,开始后移 start,直到达到最小满足条件的范围,并记录,之后继续后移 end ;循环操作,并每次取最小的范围,直至 end 达到数组尾。
class Solution(object):
def minSubArrayLen(self, target, nums):
"""
:type target: int
:type nums: List[int]
:rtype: int
"""
i = 0;
n = len(nums);
min_ = n + 1;
total = 0;
for j in range(n): # 不直接使用sum(数组切片),可以加快速度.
total += nums[j];
while (total >= target):
min_ = min(min_, j - i + 1);
total -= nums[i];
i += 1;
return 0 if min_ == n + 1 else min_;
Q:给定一个正整数 n,生成一个包含 1 到 n^2 所有元素,且元素按顺时针顺序螺旋排列的正方形矩阵。
分析:这个题目的思路非常巧妙,创建一个空的二维数组,限制数组矩阵四边的起始位置,按照顺时针依次填入数据。
class Solution(object):
def generateMatrix(self, n):
"""
:type n: int
:rtype: List[List[int]]
"""
mat = [[0 for i in range(n)] for i in range (n)]
w, s, a, d, m = 1, n, 1, n, 0;
len_ = n**2;
while(m < len_):
j_a = a - 1;
while(j_a < d):
mat[w - 1][j_a] = m + 1;
m += 1;
j_a += 1;
w = w + 1;
j_w = w - 1;
while (j_w < s):
mat[j_w][d - 1] = m + 1;
m += 1;
j_w += 1;
d = d - 1;
j_s = d ;
while(j_s >= a):
mat[s - 1][j_s - 1] = m + 1;
m += 1;
j_s -= 1;
s = s - 1;
j_a = s ;
while (j_a >= w):
mat[j_a - 1][a - 1] = m + 1;
m += 1;
j_a -= 1;
a = a + 1;
return mat
数组除了较为经典的查找、排序算法外,比较常用的思想还有:以空间换时间、双指针等。