代码随想录算法训练营第二天| 977.有序数组的平方 ,209.长度最小的子数组 ,59.螺旋矩阵II

想法:看到最后一个题的时候有些慌张,好像做过,但是没有印象了,最后在卡哥的文章下,逐渐恢复了记忆。

收获:对于二分等边界条件印象更加深刻了,复习了一部分滑动窗口知识点。

学习时长:2个小时(一直在墨迹,哈哈哈)


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

题目:给你一个按 非递减顺序 排序的整数数组 nums,返回 每个数字的平方 组成的新数组,要求也按 非递减顺序 排序。

//方法一:暴力求解,同时利用Arrays函数的特性

class Solution {
    public int[] sortedSquares(int[] nums) {
        int[] newNums = new int[nums.length];
        for (int i = 0; i < newNums.length; i++) {
            int temp = nums[i];
            int ans = (int) Math.pow(temp, 2);
            newNums[i] = ans;
        }
​
        Arrays.sort(newNums);
        return newNums;
    }
}

//双指针法:

//想法:发现该题的本质就是比较两端谁大谁小。在两端比较,进而想到了双指针(其实是看了今天的主题,双指针,哈哈哈~)

class Solution {
    // 原先没有平方的就是有序数组,只是有正有负,所以我们比较的重点就是小于零部分和最大正数那部分,看看谁的平方大。
    // 双指针法
    // left指向下标为零的元素,right指向最后一个元素。
    // 新的数组res,其中用k进行定位,先从数组的最后开始,存入目标值后向前递减。
    public int[] sortedSquares(int[] nums) {
        int left = 0;
        int right = nums.length - 1;
        int[] res = new int[nums.length];
        int k = res.length - 1;
        while (left <= right) {
            if (nums[right] * nums[right] > nums[left] * nums[left]) {
                res[k] = nums[right] * nums[right];// 先存入大值
                k--;
                right--;
            } else {
                res[k] = nums[left] * nums[left];
                k--;
                left++;
            }
        }
        return res;
    }
}

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

题目:给定一个含有 n 个正整数的数组和一个正整数 target 。
找出该数组中满足其总和大于等于 target 的长度最小的 连续子数组[numsl, numsl+1, ..., numsr-1, numsr] ,并返回其长度如果不存在符合条件的子数组,返回 0 。

//滑动窗口进行求解

所谓滑动窗口,就是不断的调节子序列的起始位置和终止位置,从而得出我们要想的结果

一旦sum>=target,我们就不断压缩这个子数组的长度,找到能实现要求的最小长度。

class Solution {
    //滑动窗口
	public int minSubArrayLen(int target, int[] nums) {
		int slow = 0;
		int ans = Integer.MAX_VALUE;
		int sum = 0;// 子数组的和
		for (int fast = 0; fast < nums.length; fast++) {
			sum += nums[fast];
			while (sum >= target) {
				int len = fast - slow + 1;
				ans = Math.min(ans, len);
				sum -= nums[slow];
				slow++;
			}
		}
		return ans == Integer.MAX_VALUE ? 0 : ans;
	}
}

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

题目:给你一个正整数 n ,生成一个包含 1 到 n^2 所有元素,且元素按顺时针顺序螺旋排列的 n * n 正方形矩阵 matrix 。

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

//注意事项:

这里一圈下来,我们要画每四条边,这四条边怎么画,每画一条边都要坚持一致的左闭右开,或者左开右闭的原则,这样这一圈才能按照统一的规则画下来。

按照左闭右开的原则,来画一圈,大家看一下:

这里每一种颜色,代表一条边,我们遍历的长度,可以看出每一个拐角处的处理规则,拐角处让给新的一条边来继续画。

这也是坚持了每条边左闭右开的原则。

//上面的话摘抄自代码随想录//

//解释都在代码注释中,哈哈哈

class Solution {
	// 本题我们采用的思想是左闭右开!!!(一定要注意)
    
	public int[][] generateMatrix(int n) {
		int[][] res = new int[n][n];
		int startX = 0, startY = 0;
		int offset = 1;
		int loop = 1;// 一次循环的层数
		int i, j;// i:竖着的,j:横着的
		int count = 1;// 矩阵的需要的元素
		while (loop <= n / 2) {
            //注意本体的左闭右开是指,在一行或一列中留下一个不处理,给下一个进行处理。。。
			// 赋值的顺序:自左向右,自上向下,自右向左,自下向上
			// 自左向右
			for (j = startY; j < n - offset; j++) {// 左闭右开
				res[startX][j] = count++;
			}
			// 自上向下
			// 此时的j处于遍历的一行中的最后一个元素(因为最后面j++了嘛)
			for (i = startX; i < n - offset; i++) {
				res[i][j] = count++;
            
            // 自右向左
			for (; j > startY; j--) {// 注意:j > startY 这里没有等号,因为左闭右开的原则,只是此时反了过来
				res[i][j] = count++;
			}
			// 自下向上
			for (; i > startX; i--) {
				res[i][j] = count++;
			}
…			// 此时才循环完一层
			// 为下一层做准备
			startX++;
			startY++;
			offset++;
			loop++;
		}
// 特殊点:若n为奇数,通过画个图发现,最里面的那个元素没法赋值,所以我们要进行单独赋值
		if (n % 2 == 1) {
			res[startX][startY] = count;// 这里是count的缘故是:之前在最后赋值完count是++的状态,count++先赋值,再自增,所以我们利用了前面已经自增过的count
		}
		return res;
	}
}

感谢您的观看,希望对您有一定的帮助。

  • 3
    点赞
  • 8
    收藏
    觉得还不错? 一键收藏
  • 1
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值