260. Single Number III

本文介绍两种方法来找出数组中仅出现一次的两个数。第一种方法使用Java集合类Set,通过添加和移除元素来筛选结果。第二种方法通过位操作实现更高效查找,包括先进行异或运算再按特定位划分数组并分别计算。

问题描述:

Given an array of numbers nums, in which exactly two elements appear only once and all the other elements appear exactly twice. Find the two elements that appear only once.

For example:

Given nums = [1, 2, 1, 3, 2, 5], return [3, 5].

给定一个数组,该数组中有两个数只出现一次而其他数都刚好出现两次,找到这两个数并返回一个含有这两个数的数组,顺序不care。

方法一:

使用java的集合类set,遍历数组,对于每一个数字,若集合中没有则放入其中;若有则将其从集合中移除。

public class Solution {
    public int[] singleNumber(int[] nums) {
        Set<Integer> set = new HashSet<Integer>();
        for(int i=0;i<nums.length;i++){
            if(set.contains(nums[i])){
                set.remove(nums[i]);
            }
            else{
                set.add(nums[i]);
            }
        }
        Object[] res;
        res = set.toArray();
        int[] result = {(int)res[0],(int)res[1]};
        return result;
    }
}


方法二:

可以考虑将所有的数按位异或,便得到所求两个数按位异或的结果。这里使用了一个非常巧妙的方法将两者分开,我们注意到由于这两个数是肯定不相等的,那么在异或运算之后结果的比特位肯定会有1的情况,这是表示这两个数在该比特位一个是0,一个是1。恰恰我们可以利用这一点,将两者分开!我们假设这个比特位是第k位。

  此时,我们可以再次遍历数组,将元素中第k比特位为0和1的分开成两队单独进行异或运算。这样一来,我们不仅保证了两队中都会有一个最后的独数,而且还确保了这两个队列中有且仅有这个数是单独的,其余元素仍然是成对出现。所以,这两组队列分别进行异或运算之后的结果就是我们想要的答案。

public class Solution {  
    public int[] singleNumber(int[] nums) {  
        int[] result = new int[2];  
        int temp = 0;  
        for(int i = 0; i < nums.length; i++)  
            temp ^= nums[i];  
        int j = 1;  
        while((temp & j) != j)  
            j <<= 1;  
        for(int i = 0; i < nums.length; i++) {  
            if((nums[i] & j) == j)  
                result[0] ^= nums[i];  
            else  
                result[1] ^= nums[i];  
        }  
        return result;  
    }  
}




评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值