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

目录

977.有序数组的平方

题目建议: 

暴力求解法:快排函数sort()

双指针排序法:

209.长度最小的子数组 

题目建议: 

滑动窗口法:(不熟练)

59.螺旋矩阵II

题目建议:  

逻辑梳理:左闭右开的原则(不熟练)


今天的几道题,用暴力求解的方法总是超出时间限制,自己调了一下反倒弄复杂了,后面遇到这种对复杂度有限制的题,就直接用对应的算法做吧。


977.有序数组的平方

题目链接:977.有序数组的平方

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

  • 请你设计时间复杂度为 O(n) 的算法解决本问题

题目建议: 

本题关键在于理解双指针思想。

暴力求解法:快排函数sort()

class Solution {
public:
    vector<int> sortedSquares(vector<int>& nums) {
        int len = nums.size();

        for(int i = 0; i < len; ++i){
            nums[i] =  nums[i]*nums[i];
        }

        sort(nums.begin(), nums.end()); // C++快排函数

        return nums;
    }
};

 起初是通过选择排序法写的,但是超出了时间限制,这个和使用的排序方法有关,选择排序的时间复杂度O(n^2),快速排序的时间复杂度O(nlogn)。十大经典排序算法(动图演示) 

双指针排序法:

class Solution {
public:
    vector<int> sortedSquares(vector<int>& nums) {
        //双指针
        int len = nums.size();
        vector<int> new_nums(len);

        int left_index = 0;
        int right_index = len-1;

        while(left_index <= right_index){
            len--;
            if( pow(nums[left_index],2) < pow(nums[right_index], 2) ){
                new_nums[len] = pow(nums[right_index], 2);
                right_index--;
            } else{
                new_nums[len] = pow(nums[left_index], 2);
                left_index ++;
            }
 
        }

        return new_nums;
    }
};

209.长度最小的子数组 

题目链接:209.长度最小的子数组

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

  • 如果你已经实现 O(n) 时间复杂度的解法, 请尝试设计一个 O(n log(n)) 时间复杂度的解法。

题目建议: 

本题关键在于理解滑动窗口,这个滑动窗口看文字讲解 还挺难理解的,建议大家先看视频讲

解。  拓展题目可以先不做。

滑动窗口法:(不熟练)

class Solution {
public:
    int minSubArrayLen(int target, vector<int>& nums) {
        // 滑动窗口
        int len = nums.size();
        int min_len = INT_MAX; // 存储最小的长度
        int val = 0; 

        int start_index = 0;
        int end_index = 0;

        for(; end_index < len; end_index++){
            val += nums[end_index];
            while(val >= target){
                min_len = min_len < (end_index - start_index + 1) ? min_len : (end_index - start_index + 1);
                val -= nums[start_index++];    
            }          
        }
        return min_len == INT_MAX ? 0 : min_len; //如果没有被赋值,则返回0
    }
};

59.螺旋矩阵II

题目链接:59.螺旋矩阵II

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

题目建议:  

本题关键还是在转圈的逻辑,在二分搜索中提到的区间定义,在这里又用上了。 

逻辑梳理:左闭右开的原则(不熟练)

class Solution {
public:
    vector<vector<int>> generateMatrix(int n) {
        // 左闭右开
        vector<vector<int>> mat(n, vector<int>(n, 0));//初始化n*n数组
        int startx = 0, starty = 0; // 定义每循环一个圈的起始位置
        int offset = 1; // 需要控制每一条边遍历的长度,每次循环右边界收缩一位

        int num = 0;//矩阵中每个元素赋值
        int end = n-1;
        int loop = n / 2;
        int i,j;
        while(loop --){

            i = startx;
            j = starty;

            //从左到右
            for( j = starty; j < n-offset; j++){
                mat[i][j] = ++num;
            }
            //从上到下
            for( i = startx; i < n-offset; i++){
                mat[i][j] = ++num;
            }
            //从右到左
            for(; j > starty; j--){
                mat[i][j] = ++num;
            }
            //从下到上
            for(; i > startx; i--){
                mat[i][j] = ++num;
            }

            startx++;
            starty++;
            offset += 1;
        }

        // 如果n为奇数,单独给矩阵最中间的位置赋值
        if(n % 2){
            mat[n/2][n/2] = n*n;
        }  

        return mat;

    }
};


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

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

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

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值