0
点赞
收藏
分享

微信扫一扫

剑指Offer-03 数组中重复的数字

烟中雯城 2022-04-16 阅读 49
c语言

方案一:暴力求解

暴力求解的思路非常的直接:

  • 遍历数组中的每个元素,然后在剩下的元素中寻找是否存在相同的元素

代码如下:

public int findRepeatNumber(int[] nums) {
    for (int i = 0; i < nums.length; i++) {
        for (int j = i + 1; j < nums.length; j++) {
            if (nums[i] == nums[j]) {
                return nums[i];
            }
        }
    }
    return -1;
}

算法复杂度分析:

  • 时间复杂度是 O(n^2)
  • 空间复杂度是 O(1)

而本题对n做了一个限制


方案二:哈希查找

使用哈希表后的算法步骤是:

  •         先初始化一个哈希表 (HashSet)
  •         然后遍历每一个元素,分别对每一个元素做如下的处理:

代码如下:

public int findRepeatNumber(int[] nums) {
    // 1. 初始化一个哈希表
    Set<Integer> set = new HashSet<>();
    for (int i = 0; i < nums.length; i++) {
        // 2. 判断当前元素是否已经存在
        if (set.contains(nums[i])) {
            // 如果存在,则直接返回
            return nums[i];
        }
​
        // 否则的话,将当前元素放入到哈希表中,方便后续的查找判重
        set.add(nums[i]);
    }
    return -1;
}

 算法复杂度分析:

  • 时间复杂度是 O(n)
  • 空间复杂度是 O(n)

方案三:数组代替哈希表

在题目中,有一个信息,我们需要注意下,那就是数组中每个元素的大小在 0 ~ n - 1 的范围内。利用这个信息,我们就可以使用数组代替上面方案二的哈希表,主要的思路是:

代码如下:

public int findRepeatNumber(int[] nums) {
    // 1. 初始化一个数组
    int[] bucket = new int[nums.length];
    Arrays.fill(bucket, -1);
​
    for (int i = 0; i < nums.length; i++) {
        // 2. 判断当前元素是否已经存在
        if (bucket[nums[i]] != -1) {
            // 如果存在,则直接返回
            return nums[i];
        }
​
        // 否则的话,将当前元素作为索引,当前元素的下标作为值,填入数组中,
        // 方便后续的查找判重
        bucket[nums[i]] = i;
    }
    return -1;
}

算法复杂度分析:

  • 时间复杂度是 O(n)
  • 空间复杂度是 O(n)

可以看出,时间复杂度和空间复杂度都是和用哈希表的解决方案是一样的。但是使用数组绝对会有性能的提高,主要表现在如下的两个方面:

举报

相关推荐

0 条评论