【代码随想录】刷题笔记——数组篇

目录

704. 二分查找

27. 移除元素

977. 有序数组的平方

209. 长度最小的子数组

59. 螺旋矩阵 II


704. 二分查找

class Solution {
    public int search(int[] nums, int target) {
        int left = 0;
        int right = nums.length - 1;
        while (left <= right) {
            int mid = left + (right - left) / 2;
            if (nums[mid] == target) {
                return mid;
            }
            else if (nums[mid] < target) {
                left = mid + 1;
            }
            else {
                right = mid - 1;
            }
        }
        return -1;
    }
}

int mid = left + (right - left) / 2; 而不是 (left + right) / 2;

可以理解为:左起点+长度的一半=中点位置

这样可以防止溢出(两个 int 相加)

 

27. 移除元素

思路

由于题目要求删除数组中等于 val 的元素,因此输出数组的长度一定小于等于输入数组的长度,我们可以把输出的数组直接写在输入数组上。可以使用双指针:右指针 right 指向当前将要处理的元素,左指针 left 指向下一个将要赋值的位置。

  • 如果右指针指向的元素不等于 val,它一定是输出数组的一个元素,我们就将右指针指向的元素复制到左指针位置,然后将左右指针同时右移;
  • 如果右指针指向的元素等于 val,它不能在输出数组里,此时左指针不动,右指针右移一位。

整个过程保持不变的性质是:区间 [0,left) 中的元素都不等于 val。当左右指针遍历完输入数组以后,left 的值就是输出数组的长度。

这样的算法在最坏情况下(输入数组中没有元素等于 val),左右指针各遍历了数组一次。

代码

class Solution {
    public int removeElement(int[] nums, int val) {
        int left = 0;
        int right = left;
        while (right < nums.length) {
            if (nums[right] != val) {
                nums[left] = nums[right];
                left++;
            }
            right++;
        }
        return left;
    }
}

 

977. 有序数组的平方

解法一:

class Solution {
    public int[] sortedSquares(int[] nums) {
        for (int i = 0;i < nums.length;i++) {
            nums[i] *= nums[i];
        }
        Arrays.sort(nums);
        return nums;
    }
}

数组排序API:Arrays.sort(nums);

解法二:

相向双指针:从大到小合并

代码

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

209. 长度最小的子数组

思路:滑动窗口

代码

class Solution {
    public int minSubArrayLen(int target, int[] nums) {
        int n = nums.length;
        int result = Integer.MAX_VALUE;   
        int left = 0;
        int right = 0;
        int temp = 0;
        while (right < n) {
            temp += nums[right];
            while (temp >= target) {
                result = Math.min(result,right - left + 1);
                temp -= nums[left];
                left++;
            }
            right++;
        }
        return result == Integer.MAX_VALUE ? 0:result;
    }
}

1. Integer.MAX_VALUE 相当于 C++中的 INT_MAX

2. Math.min(a,b);    最小值

59. 螺旋矩阵 II

思路

代码:

class Solution {
    public int[][] generateMatrix(int n) {
        int[][] arr = new int[n][n];
        int t = 0;      // top
        int b = n-1;    // bottom
        int l = 0;      // left
        int r = n-1;    // right
        int num = 0;
        while (num != n*n) {
            for (int i = l;i <= r;i++) {
                arr[t][i] = ++num;
            }
            t++;
            for (int i = t;i <= b;i++) {
                arr[i][r] = ++num;
            }
            r--;
            for (int i = r;i >= l;i--) {
                arr[b][i] = ++num;
            }
            b--;
            for (int i = b;i >= t;i--) {
                arr[i][l] = ++num;
            }
            l++;
        }
        return arr;
    }
}

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值