class Solution {
public int[] sortedSquares(int[] nums) {
int[] result = new int[nums.length];
int left = 0;
int right = nums.length - 1;
int index = nums.length - 1;
while(left<=right){
if(nums[right]*nums[right]>nums[left]*nums[left]){
result[index] = nums[right]*nums[right];
index --;
right --;
}
else{
result[index] = nums[left] * nums[left];
index --;
left ++;
}
}
return result;
}
}
思路:
- 首先,为结果数组
result
分配空间。 - 使用两个指针
left
和right
,分别初始化为数组的开始和结束。 - 初始化
index
为nums.length - 1
,这是结果数组的最后一个位置。 - 使用一个
while
循环,当left
小于等于right
时:- 比较
nums[left]
和nums[right]
的平方值。 - 如果
nums[right]
的平方大于nums[left]
的平方,则将nums[right]
的平方放入result[index]
,然后将index
和right
都减 1。 - 否则,将
nums[left]
的平方放入result[index]
,然后将index
减 1,left
加 1。
- 比较
- 返回结果数组
result
。
这个方法的主要思想是由于输入数组是有序的,所以数组的两端可能包含最大的平方值。因此,从两端开始,选择最大的平方值并将其放入结果数组的相应位置。
class Solution {
public int minSubArrayLen(int target, int[] nums) {
int sum = 0;
int result = Integer.MAX_VALUE;
int left = 0;
for(int right = 0; right < nums.length; right++){
sum += nums[right];
while(sum>=target){
result = Math.min(result, right - left +1);
sum -= nums[left];
left++;
}
}
return result == Integer.MAX_VALUE? 0:result;
}
}
思路:
经典的滑动窗口问题
-
初始化
sum
为 0,result
为Integer.MAX_VALUE
(用于存放最小长度值),left
为 0(代表窗口左边界)。 -
使用一个
for
循环,通过right
指针遍历数组nums
。 -
在每次迭代中,将
nums[right]
加到sum
中。 -
当
sum
大于或等于target
时:- 使用
Math.min
更新result
的值为result
和(right - left + 1)
中的较小值,其中(right - left + 1)
是当前滑动窗口的长度。 - 从
sum
中减去nums[left]
的值,然后将left
指针右移一位,收缩滑动窗口的大小。
- 使用
-
如果
result
仍然是Integer.MAX_VALUE
(代表没有找到符合条件的子数组),则返回 0,否则返回result
。
class Solution {
public int[][] generateMatrix(int n) {
int loop = 0; // 控制循环次数
int[][] res = new int[n][n];
int start = 0; // 每次循环的开始点(start, start)
int count = 1; // 定义填充数字
int i, j;
while (loop < n / 2) { // 判断边界后,loop从1开始
loop++;
// 模拟上侧从左到右
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;
}
}
思路:
-
初始化边界和变量:
loop
用于控制循环次数,理论上最多只需要循环 n/2 次。start
表示每次循环的起始点,用于控制当前循环的起始位置。count
是用于填充的数字,从1开始。
-
开始填充循环:
-
while (loop < n / 2)
:最多循环 n/2 次,例如当 n=4 时,只需循环 2 次;当 n=5 时,需要循环 2 次,但中心点的数字需要额外填充。在每次的循环中:注意左闭右开区间
for (j = start; j < n - loop; j++)
:填充上方的数字。for (i = start; i < n - loop; i++)
:填充右侧的数字。for (; j >= loop; j--)
:填充下方的数字。for (; i >= loop; i--)
:填充左侧的数字。
-
-
更新起始点并进行下一次循环:
start++
,向内收缩一圈,为下一个螺旋做准备,即起始点右移和下移。
-
处理中心点(当 n 是奇数时):
- 如果
n
是奇数,那么在所有螺旋循环结束后,矩阵的中心点仍然是空的。需要最后填充这个中心点。
- 如果