美文网首页
数组(二) 存在重复

数组(二) 存在重复

作者: 疏花 | 来源:发表于2019-07-19 16:11 被阅读0次

    题目:

    给定一个整数数组,判断是否存在重复元素。
    如果任何值在数组中出现至少两次,函数返回 true。如果数组中每个元素都不相同,则返回 false。
    原题地址

    示例 1:

    输入: [1,2,3,1]
    输出: true

    示例 2:

    输入: [1,2,3,4]
    输出: false

    示例 3:

    输入: [1,1,1,3,3,4,3,2,4,2]
    输出: true

    此题比较简单,主要在于思路。

    思路一:

    最简单的方法是嵌套循环,每个数依次与它前面的数进行比较,相等则返回true。

      private static boolean containsDuplicate(int[] nums) {
            for (int i = 0; i < nums.length; i++) {
                for (int j = 0; j < i; j++) {
                    if (nums[i] == nums[j]) {
                        return true;
                    }
                }
            }
            return false;
      }
    

    这种解法的时间复杂度是 O(n2),时间花费较久。

    思路二:

    换一种思路来,如果数组本身是有序的,那么重复的元素必定处于相邻上,那么只要比较相邻元素就行了。

     public boolean containsDuplicate(int[] nums) {
            Arrays.sort(nums);
            for (int i=0; i < nums.length - 1; i++){
                if(nums[i] == nums[i+1]){
                    return true;
                }
            }
            return false;
        }
    

    思路三:

    利用Set元素不重复的性质来去重。

     public boolean containsDuplicate(int[] nums) {
            Set<Integer> numSet = new HashSet<>(nums.length);
            for (int i: nums){
                if(numSet.contains(i)){
                    return true;
                }
                numSet.add(i);  
            }
            return false;
        }
    

    思路四:

    看了下LeetCode上耗时最短的解法,思路是利用boolean数组和&操作符。
    &操作运算规则:将两个数都转为二进制,然后从高位开始比较,如果两个数都为1则为1,否则为0。
    如:129&128.
    129转换成二进制就是10000001,128转换成二进制就是10000000。从高位开始比较得到,得到10000000,即128.

    public boolean containsDuplicate(int[] nums) {
            if (nums.length < 1 || nums[0] == 237384 || nums[0] == -24500)
                return false;
            boolean[] bc = new boolean[1024];
            for (int num : nums) {
                /*1023的二进制为1111111111,num&1023的结果为num
                 如果对应位置已经为true,说明存在相同数字,返回true*/
                if (bc[num & 1023])
                    return true;
                //将boolean数组中对应位置设为true
                bc[num & 1023] = true;
            }
            return false;
        }
    

    但是此解法存在问题,上面说num&1023的结果为num,只限于num<=1023的情况,当num>1023时(比如1024),1024&1023结果为0,此时如果数组为[0,1024],0&1023和0&1024结果都为0,此解法返回true,显然与预期不符。因此这个解法只适用于nums中的元素<=1023的情况。

    相关文章

      网友评论

          本文标题:数组(二) 存在重复

          本文链接:https://www.haomeiwen.com/subject/mvojlctx.html