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

41 阅读2分钟

JAVA数组相关操作

一维数组的创建并同时初始化: 数组数据类型  数组名 = new 数组数据类型[数组空间];

int array [] = new int [8];

int最大值的表示

Integer.MAX_VALUE

最小值 Math.min(A, B)

977.有序数组的平方

我的解法

我的做题记录之依稀记得解法但执行出错版。

① 如果数组长度为1,直接返回该元素的平方

② 如果数组元素正负一致(全为正或者全为负),因为数组本身就是有序的,所以依次做平方返回数组即可

③ 剩下的情况就是整个数组中有正也有负。那么就需要双指针解法,从正负相邻的分界两个元素开始,一个往左(小)一个往右(大)比较,把较小的填入新数组中。

我总是报这个错误:java.lang.ArrayIndexOutOfBoundsException

class Solution {
    public int[] sortedSquares(int[] nums) {
        //数组初始化和数组插入
        int res [] = new int [nums.length];
        if(nums.length == 1) {
            res[0]=nums[1]*nums[1];
            return res;
        }

        //数组符号一样
        if(nums[0]>=0 || nums[nums.length-1]<=0) {
            int i = 0;
            while(i!=nums.length) {
                nums[i] = nums[i]*nums[i];
                i++;
            }
            return nums;
        }
  
        // int j = 0;
        // while(j<nums.length && nums[j]<=0) j++; // j>0
        // int i = j-1;

        int j = 0;
        while(j<nums.length && nums[j] != 0) j++;
        int i = j-1;
        j = j+1;
        int k = 0;
        res[k++] = 0;
        while(i != -1 || j != nums.length) {
            if(i == -1) {
                res[k++] =  nums[j]*nums[j];
                j++;
            } else if(j == nums.length) {
                res[k++] =  nums[i]*nums[i];
                i--;
            } else {
                if(nums[i]*nums[i] > nums[j]*nums[j]) {
                    res[k++] =  nums[j]*nums[j];
                    j++;
                } else {
                    res[k++] =  nums[i]*nums[i];
                    i--;
                }
            }
        }
        return res;
    }
}

正确解法

遍历数组同时平方,再用数组自带的排序,复杂度是:O(nlogn)。 啊!!!为什么我双指针的方向又和正确思路相反…原来可以两边向中间逼近……

class Solution {
    public int[] sortedSquares(int[] nums) {
        int res[] = new int[nums.length];
        int i = 0, j = nums.length-1;
        int k = nums.length-1;
        while(i <= j) {
            if(nums[i]*nums[i] >= nums[j]*nums[j]) {
                res[k--] = nums[i]*nums[i];
                i++;
            } else {
                res[k--] = nums[j]*nums[j];
                j--;
            }
        }
        return res;
    }
}

image.png

209.长度最小的子数组

哈哈 完全忘记怎么做了……好像是做过且还写过博客……鱼的记忆……

① 暴力解法,两个for循环

② 滑动窗口

当目前的sum没有大于等于target时,right指针右推;当达到了时,left左推试图减小这个窗口的长度。

class Solution {
    public int minSubArrayLen(int target, int[] nums) {
        int left = 0, sum = 0;
        int result = Integer.MAX_VALUE;
        for(int right = 0 ; right < nums.length ; right ++) {
            sum += nums[right];
            while(sum >= target) {
                //这个等于为什么需要?这个为什么是while
                result = Math.min(result, right - left + 1);
                sum -= nums[left];
                left++;
            }
        }
        return result == Integer.MAX_VALUE ? 0 : result;
    }
}

59.螺旋矩阵II

明天看。。