代码随想录训练营-数组part02
解题思路-- 977 有序数组的平方
题目特征: 有序数组经过转换,变化为有序数组
解题思考:
- 双指针遍历,左右两指针进行对比,按照对比后结果,按顺序存放至新数组
- 对比成功的指针进行移动,重新进行step1
- 当两指针进行汇合时进行最后一次对比
class Solution {
public int[] sortedSquares(int[] nums) {
// 数组有序,正负皆有
// 重新定义数组进行存储,老数组双指针遍历,取大的数据倒序放到新的数组中
int leftPoint = 0;
int rightPoint = nums.length -1;
int[] newNums = new int[nums.length];
int index = nums.length -1;
while(leftPoint <= rightPoint){
int leftNum = nums[leftPoint] * nums[leftPoint];
int rightNum = nums[rightPoint] * nums[rightPoint];
if (leftNum > rightNum){
newNums[index] = leftNum;
leftPoint++;
}else{
newNums[index] = rightNum;
rightPoint--;
}
index--;
}
return newNums;
}
}
解题思路-- 209.长度最小的子数组
题目特征: 有序数组中查找符合条件的最优子数组
解题思考:
- 数组优先考虑双指针
- 母数组进行符合条件的子数组查找,优先考虑滑动窗口
- 滑动窗口找好追外层for循环采用右指针
- for中套取while进行左指针滑动
class Solution {
public int minSubArrayLen(int target, int[] nums) {
// 滑动窗口解法 双指针
// 循环右指针,累积左指针至右指针之间的数组元素和
// 当数组元素和>target时,记录当前最大长度j-i+1,左指针开始右移
// 注意 因为右指针相对静止,所以要在for循环中加while进行左指针遍历
int leftPoint = 0;
int result = Integer.MAX_VALUE;
int sum = 0;
for (int rightPoint = 0; rightPoint < nums.length ; rightPoint++ ){
sum += nums[rightPoint];
while(sum >= target){
result = Math.min(rightPoint - leftPoint +1, result);
sum = sum - nums[leftPoint];
leftPoint++;
}
}
return result == Integer.MAX_VALUE ? 0 : result;
}
}
解题思路-- 59.螺旋矩阵II
题目特征: 有序自然整数组成二维数组
解题思考:
- 此类问题基本上考虑数值的存放位置
- 每条线段的处理逻辑应相同 例如均采用左闭右开
- 找好每条线段的起始位置和边界条件即可
- 每一圈循环的起始位置和边界条件谨慎考虑
class Solution {
public int[][] generateMatrix(int n) {
int[][] array = new int[n][n];
// 当前圈数
int loop = 0;
// 当前待赋值数据
int currentNum = 1;
// 每圈初始行位置
int start =0;
// 行初始值
int i=0;
// 列初始值
int j=0;
// 每次遍历为一圈
while(loop++ < n/2){
// 遍历原则为左闭右开 [)
// 第一行 j为当前列 遍历 n-loop为列的开区间上限
for (j=start; j<n-loop;j++){
array[start][j] = currentNum++;
}
// 最后一列
for(i = start; i< n-loop; i++){
array[i][j] = currentNum++;
}
// 最后一行
for(;j >= loop;j--){
array[i][j] = currentNum++;
}
// 第一列
for(;i >= loop; i--){
array[i][j] = currentNum++;
}
start ++;
}
// 最中间元素
if(n%2 == 1){
array[n/2][n/2] = currentNum;
}
return array;
}
}