977有序数组的平方977. 有序数组的平方 - 力扣(LeetCode)代码随想录 (programmercarl.com)
给你一个按 非递减顺序 排序的整数数组 nums,返回 每个数字的平方 组成的新数组,要求也按 非递减顺序 排序。
非递减顺序即为可重复的升序排列,第一时间想到的是将所有元素平方后对整个数组进行排序,时间复杂度为O(n+logn),但是较为暴力。
所以使用另一种思路,因为本来是升序排列,所以平方后最大的数据应当是数组两边的第一个数,所以采用双指针法,一个指向左边第一个数,另一个指向右边第一个数,对两数平方进行比较,将较大值放入结果数组的最后一个位置,再对指针进行调整,直到将所有数据放入结果数组,时间复杂度仅为O(n)。
实现如下:
class Solution {
public int[] sortedSquares(int[] nums) {
for(int i=0;i<nums.length;i++){
nums[i]=nums[i]*nums[i];
}
Arrays.sort(nums);
return nums;
}
}
class Solution {
public int[] sortedSquares(int[] nums) {
int left=0,right=nums.length-1;
int k=nums.length-1;
int[] result=new int[nums.length];
while(left<=right){
if(nums[right]*nums[right]>=nums[left]*nums[left]){
result[k--]=nums[right]*nums[right];
right--;
}
else{
result[k--]=nums[left]*nums[left];
left++;
}
}
return result;
}
}
209.长度最小的子数组代码随想录 (programmercarl.com)209. 长度最小的子数组 - 力扣(LeetCode)
给定一个含有 n 个正整数的数组和一个正整数 target 。 找出该数组中满足其和 ≥ target 的长度最小的 连续子数组 [numsl, numsl+1, ..., numsr-1, numsr] ,并返回其长度。如果不存在符合条件的子数组,返回 0 。
暴力法为两层循环,但是力扣要求时间复杂度为O(n),所以不能通过,所以通过另一种思路,个人感觉类似双指针,叫做滑动窗口法,首先遍历并将元素加到和中,左边指针不动,右边指针遍历,当和大于target时,记录当前长度,并开始向后移动左边指针,直到和小于target,最后即可通过相当于两次遍历完成搜索。
实现如下:
class Solution {
public int minSubArrayLen(int target, int[] nums) {
int min=nums.length+1;
int sum=0;
int length=0;
int i=0;//滑动窗口起始位置
for(int j=0;j<nums.length;j++){
sum+=nums[j];
while(sum>=target){
length=j-i+1;
if(length<min)
min=length;
sum-=nums[i++];
length--;
}
}
if(min==nums.length+1)
return 0;
return min;
}
}
59螺旋矩阵59. 螺旋矩阵 II - 力扣(LeetCode)代码随想录 (programmercarl.com)
给你一个正整数 n ,生成一个包含 1 到 n2 所有元素,且元素按顺时针顺序螺旋排列的 n x n 正方形矩阵 matrix 。
刚开始看到这个题目没有什么思路,有想过模拟转圈的操作,但是不知道怎么实现,后来发现对于n的数只有两种情况,一种是n是奇数,那么循环n/2次之后中间需要再填一次数,一种是n是偶数,只需要循环n/2次,每一圈循环遵循左闭右开原则,所以每一条边只需填n-循环数次即可,其他的只要按照正常正方形循环即可。实现如下:
class Solution {
public int[][] generateMatrix(int n) {
int count=1;
int loop=0;
int start=0;
int[][] res=new int[n][n];
int i,j;
while(loop++<n/2){//只需n/2次循环
for(j=start;j<n-loop;j++)
res[start][j]=count++;
for(i=start;i<n-loop;i++)
res[i][j]=count++;
for(;j>=loop;j--)
res[i][j]=count++;
for(;i>=loop;i--)
res[i][j]=count++;
start++;
}
if(n%2==1)
res[start][start]=count;
return res;
}
}
总结一下数组类题目主要有三种方法:双指针法、滑动窗口法(个人觉得和双指针类似)、模拟法。