力扣 977有序数组的平方 209长度最小的子数组 59螺旋矩阵II

题目链接:

977. 有序数组的平方 - 力扣(LeetCode)

209. 长度最小的子数组 - 力扣(LeetCode)

59. 螺旋矩阵 II - 力扣(LeetCode)

一、有序数组的平方。

直接暴力。通过是通过了,但是时间内存都太大┭┮﹏┭┮,待优化。

力扣 977有序数组的平方 209长度最小的子数组 59螺旋矩阵II_第1张图片

 排序输出用了sort,好了一点点。

力扣 977有序数组的平方 209长度最小的子数组 59螺旋矩阵II_第2张图片

看看官方题解,双指针法。

 

“使用两个指针分别指向位置 0 和 n−1,每次比较两个指针对应的数,选择较大的那个逆序放入答案并移动指针。这种方法无需处理某一指针移动至边界的情况。”

力扣 977有序数组的平方 209长度最小的子数组 59螺旋矩阵II_第3张图片

 二、长度最小的子数组。

还是暴力。结果,还有几个样例通过不了。

看题解。

使用队列,用两个指针,一个指向队头一个指向队尾

class Solution {
              public int minSubArrayLen(int target, int[] nums) {
        int i = 0, j = 0, min = Integer.MAX_VALUE;//i为起始位置,j为终止位置,min先赋最大值
        int sum=0;
        while (j< nums.length) {
            sum += nums[j];
            while (sum >= target) {
                min = Math.min(min, j - i+1);
                sum -= nums[i++];
            }
            j++;
        }
        return min == Integer.MAX_VALUE ? 0 : min;

    }
}

三、螺旋矩阵II。

晕头转向  φ(◎ロ◎;)φ

直接听卡哥的视频讲解。

一入循环深似海 | LeetCode:59.螺旋矩阵II_哔哩哔哩_bilibili

保持一个原则,对每个边进行左闭右开的赋值。判断出转了n/2圈,最后时也要通过判断n%2是否等于1给n为奇数时的最后一个数单独赋值(奇数时,里面只是一个点,不用转圈了)。

在力扣解答里发现一个大神的解法!

Krahets

class Solution {
    public int[][] generateMatrix(int n) {
// 生成一个 n×n 空矩阵 res,随后模拟整个向内环绕的填入过程:
// 定义当前左右上下边界 left,right,top,bottom,初始值 count = 1,迭代终止值 target = n * n;
// 当 count <= target 时,始终按照 从左到右 从上到下 从右到左 从下到上 填入顺序循环,每次填入后:
// 执行 count += 1:得到下一个需要填入的数字;
// 更新边界:例如从左到右填完后,上边界 t += 1,相当于上边界向内缩 1。
// 使用count <= target而不是left < right || top < bottom作为迭代条件,是为了解决当n为奇数时,矩阵中心数字无法在迭代过程中被填充的问题。
// 最终返回 res 即可。
        int left = 0, right = n-1, top = 0, bottom = n-1;
        int count = 1, target = n * n;
        int[][] res = new int[n][n];
        //for循环中变量定义成i或j的细节:按照通常的思维,i代表行,j代表列
        //这样,就可以很容易区分出来变化的量应该放在[][]的第一个还是第二个
        //对于变量的边界怎么定义:
            //从左向右填充:填充的列肯定在[left,right]区间
            //从上向下填充:填充的行肯定在[top,bottom]区间
            //从右向左填充:填充的列肯定在[right,left]区间
            //从下向上填充:填充的行肯定在[bootom,top]区间
        //通过上面的总结会发现边界的起始和结束与方向是对应的
        while(count <= target){
            //从左到右填充,相当于缩小上边界
            for(int j = left; j <= right; j++) res[top][j] = count++;
            //缩小上边界
            top++;
            //从上向下填充,相当于缩小右边界
            for(int i = top; i <=bottom; i++) res[i][right] = count++;
            //缩小右边界
            right--;
            //从右向左填充,相当于缩小下边界
            for(int j = right; j >= left; j--) res[bottom][j] = count++;
            //缩小下边界
            bottom--;
            //从下向上填充,相当于缩小左边界
            for(int i = bottom; i >= top; i--) res[i][left] = count++;
            //缩小左边界
            left++;
        }
        return res;
}
}

代码随想录算法训练营第二天,虽然就三道题,比昨天少了一道,但感觉难了,时间上也花费更多┭┮﹏┭┮

坚持坚持!

你可能感兴趣的:(leetcode,矩阵,算法)