day2 数组 977.有序数组的平方 209.长度最小的 子数组 59.螺旋矩阵II
907.有序数组的平方
题目链接:[907.有序数组的平方](977. 有序数组的平方 - 力扣(LeetCode))
题干: 非递减顺序 排序的整数数组 nums
,返回 每个数字的平方 组成的新数组,要求也按 非递减顺序 排序。
思路:最简单是生成一个新的数组,对应的元素是原数组的平方,然后排序一下。
使用双指针,非递减序列,两端的平方值肯定比中间的平方值大,使用首尾指针,每次比较首尾指针指向元素的平方大小,大的放到新数组的尾部,直到遍历完所有元素。
class Solution {
public:
vector<int> sortedSquares(vector<int>& nums) {
vector<int> result(nums.size(), 0);
int left = 0;
int right = nums.size() - 1;
int index = result.size() - 1;;
while (left <= right) {
if (abs(nums[left]) <= nums[right]) {
result[index--] = nums[right] * nums[right];
right--;
} else {
result[index--] = nums[left] * nums[left];
left++;
}
}
return result;
}
};
209.长度最小的子数组
题目链接:[209.长度最小的子数组](209. 长度最小的子数组 - 力扣(LeetCode))
题干:给定一个含有 n
个正整数的数组和一个正整数 target
。
找出该数组中满足其总和大于等于 target
的长度最小的 子数组[numsl, numsl+1, ..., numsr-1, numsr]
,并返回其长度**。**如果不存在符合条件的子数组,返回 0
。
思路:使用滑动窗口,维持一个窗口left和right,不断将right指向的元素加入窗口,计算和,若和大于等于target,说明有满足条件的子数组了,此时计算窗口大小并保存一个最小的窗口值,然后将left指向的元素从窗口中剔除,直到窗口中的元素和小于target,然后再加入right指向的元素。循环往复,移动该窗口,最终获得一个最小数组的长度。
注意判断和大于target的循环位置在计算累计和之后
class Solution {
public:
int minSubArrayLen(int target, vector<int>& nums) {
int left = 0;
int right = 0;
int sum = 0;
int length = INT_MAX;
while (right < nums.size()) {
sum += nums[right];
while (sum >= target) {
length = min(length, right - left + 1);
sum -= nums[left];
left++;
}
right++;
}
return length == INT_MAX ? 0 : length;
}
};
59.螺旋矩阵II
题目链接:59.螺旋矩阵II
题干:给你一个正整数 n
,生成一个包含 1
到 n^2
所有元素,且元素按顺时针顺序螺旋排列的 n x n
正方形矩阵 matrix
。
思路:其实就是要遍历螺旋遍历一个二维矩阵,设置四个边界up、down、left、right
,然后开始循环,每次遍历一行或者一列,每次遍历完一行或者一列,需要变换一条边界,并且若该边界超过了对向的边界说明遍历完了整个二维数组,退出循环。
class Solution {
public:
vector<vector<int>> generateMatrix(int n) {
vector<vector<int>> result(n, vector<int>(n, 0));
int up = 0, down = n - 1;
int left = 0, right = n - 1;
int count = 1;
while (true) {
for (int i = left; i <= right; i++) {
result[up][i] = count++;
}
up++;
if (up > down) break;
for (int i = up; i <= down; i++) {
result[i][right] = count++;
}
right--;
if (right < left) break;
for (int i = right; i >= left; i--) {
result[down][i] = count++;
}
down--;
if (down < up) break;
for (int i = down; i >= up; i--) {
result[i][left] = count++;
}
left++;
if (left > right) break;
}
return result;
}
};