977有序数组的平方

力扣刷题 977.有序数组的平方--day2

题目分析

这道题目, 乍一看就是一个排序问题嘛,大不了计算完平方后, 再用个插入排序或者冒泡排序罢了

但是, 题目告诉我们, 这个数组原来就是有序的, 所以我们要用好
这个特点, 从而简化代码

数组在平方后, 后面那些原来为正数的顺序并没有改变, 前面的负数改变了

我的第一想法是: 将前面负数平方后的值插入后面的正数平方中, 但是如果在原来的数组上面去插入的话,涉及到数组元素的移动,事倍功半, 所以, 可以新建一个数组 result。

解法一

本质上也是双指针, 只不过每次都选出最小的那个值, 类似于选择排序

vector<int> sortedSquares(vector<int>& nums) {
    int size = nums.size();
    vector<int> result;
    //找到正负数的分界点
    int keyIndex = 0;
    while(keyIndex < size&&nums[keyIndex] < 0){
        keyIndex++;
    }
    //左右两个指针分别向左向右前进
    int left = keyIndex - 1;
    int right = keyIndex;

    while(left >= 0 && right <= size - 1){
        //选择较小值
        if(-1 * nums[left] > nums[right]){
            result.push_back(nums[right] * nums[right]);
            right++;
        }
        else{
            result.push_back(nums[left] * nums[left]);
            left--;
        }
    }

    //左侧率先完成
    if(left < 0){
        while (right <= size - 1)
        {
            result.push_back(nums[right] * nums[right]);
            right++;
        }
    }
    //右侧率先完成
    else if(right > size - 1){
        while(left >=0){
            result.push_back(nums[left] * nums[left]);
            left--;
        }
    }
    return result;
}

解法二

这个解法的重点是发现:最大值出现在最两侧

同样利用双指针, 一左一右, 每次选出最大的那个值, 有点类似于冒泡排序

vector<int> sortedSquares(vector<int>& nums) {
    int size = nums.size();
    vector<int> result(size);
    int newIndex = size - 1;
    int left = 0, right = size - 1;

    while(left <= right){
        if(abs(nums[left]) > abs(nums[right])){
            result[newIndex] = (nums[left] * nums[left]);
            newIndex--;
            left++;
        }
        else{
            result[newIndex] = (nums[right] * nums[right]);
            newIndex--;
            right--;
        }
    }
    return result;
}
posted @ 2023-04-20 20:40  chuxin_jian  阅读(20)  评论(0)    收藏  举报