leetcode

数组

26-删除重复元素

给你一个有序数组 nums ,请你 原地 删除重复出现的元素,使每个元素 只出现一次 ,返回删除后数组的新长度。

不要使用额外的数组空间,你必须在 原地 修改输入数组 并在使用 O(1) 额外空间的条件下完成。
链接:leetcode-cn.com/problems/remove-du...

class Solution {
    public int removeDuplicates(int[] nums) {
        if (nums.length == 0) {
            return 0;
        }
        if (nums.length == 1) {
            return 1;
        }
        int slow = 1;
        int fast = 1;
        // 1 2 2 3
        while (fast < nums.length) {
            if (nums[fast] != nums[fast - 1]) {
                nums[slow] = nums[fast];
                slow++;
            } 
            fast++;
        }
        return slow;
    }
}

27-移除元素

给你一个数组 nums 和一个值 val,你需要 原地 移除所有数值等于 val 的元素,并返回移除后数组的新长度。

不要使用额外的数组空间,你必须仅使用 O(1) 额外空间并 原地 修改输入数组。

元素的顺序可以改变。你不需要考虑数组中超出新长度后面的元素。
链接:leetcode-cn.com/problems/remove-el...

方法一:

    public int removeElement(int[] nums, int val) {
        // left代表下一个不等于val的下标
        int left = 0;
        // 遍历数组,只要不等于val的就赋值给num[left],同事left++
        for (int j = 0; j < nums.length; j++) {
            if (nums[j] != val) {
                nums[left] = nums[j];
                left++;
            }
        }
        return left;
    }

方法二:

/**
 * 元素的顺序可以改变,所以可以使用两个下标left、right
 * left从左向右寻找等于val的元素
 * right从右向左寻找不等于val的值
 * 最后令nums[right] = num[right]
 */
public int removeElement(int[] nums, int val) {
        int left = 0, right = nums.length - 1;
        int count = 0;
        while (left <= right) {
            while (left <= right && nums[left] != val && left < nums.length) {
                left++;
                count++;
            }
            while (left <= right && nums[right] == val && right >= 0) {
                right--;
            }
            if (left < right) {
                int temp = nums[left];
                nums[left] = nums[right];
                nums[right] = temp;
                count++;
                left++;
                right--;
            }
        }
        return count;
    }

方法三:

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

189-旋转数组

给定一个数组,将数组中的元素向右移动 k 个位置,其中 k 是非负数。

进阶:

尽可能想出更多的解决方案,至少有三种不同的方法可以解决这个问题。
你可以使用空间复杂度为 O(1) 的 原地 算法解决这个问题吗?

示例 1:

输入: nums = [1,2,3,4,5,6,7], k = 3
输出: [5,6,7,1,2,3,4]
解释:
向右旋转 1 步: [7,1,2,3,4,5,6]
向右旋转 2 步: [6,7,1,2,3,4,5]
向右旋转 3 步: [5,6,7,1,2,3,4]
链接:leetcode-cn.com/problems/rotate-ar...

暴力法会超时

// 会超时
    public void rotate(int[] nums, int k) {
        k = k % nums.length;
        for (int i = 0; i < k; i++) {
            int last = nums[nums.length - 1];
            for (int j = nums.length - 1; j > 0; j--) {
                nums[j] = nums[j - 1];
            }
            nums[0] = last;
        }
    }

通过找规律可以发现,翻转后的数组,将前k个翻转并且将剩下的(l-k)个也翻转,最后得到的数据为原始数组翻转后的结果。

因此我们可以先把整个数组翻转,然后将k个元素翻转,最后将后(l-k)个元素也翻转

public void rotate(int[] nums, int k) {
        k = k % nums.length;
        fun(nums, 0, nums.length - 1);
        fun(nums, 0, k - 1);
        fun(nums, k, nums.length - 1);
    }
    public void fun(int[] nums, int left, int right) {
        while (left < right) {
            int temp = nums[left];
            nums[left] = nums[right];
            nums[right] = temp;
            left++;
            right--;
        }
    }

300-最长递增子序列

给你一个整数数组 nums ,找到其中最长严格递增子序列的长度。

子序列是由数组派生而来的序列,删除(或不删除)数组中的元素而不改变其余元素的顺序。例如,[3,6,2,7] 是数组 [0,3,1,6,2,2,7] 的子序列。

链接:leetcode-cn.com/problems/longest-i...

class Solution {
    /**
     * dp[i] = max(dp[j] + 1, dp[i]), 0 <= j < i
     * [0,3,1,6,2,2,7]
     */
    public int lengthOfLIS(int[] nums) {
        if (nums.length == 1) {
            return 1;
        }
        int[] dp = new int[nums.length];
        dp[0] = 1;
        int max = 1;
        for (int i = 1; i < nums.length; i++) {
            dp[i] = 1;
            for (int j = 0; j < i; j++) {
                // 找到比当前i的值小了
                if (nums[j] < nums[i]) {
                    dp[i] = Math.max(dp[j] + 1, dp[i]);
                    max = Math.max(max, dp[i]);
                }
            }
        }
        return max;
    }
}
本作品采用《CC 协议》,转载必须注明作者和本文链接
讨论数量: 0
(= ̄ω ̄=)··· 暂无内容!

讨论应以学习和精进为目的。请勿发布不友善或者负能量的内容,与人为善,比聪明更重要!