【初级算法】-- 5.只出现一次的数字(java中的异或操作)

版权声明:本文为博主原创文章,未经博主允许不得转载。 https://blog.csdn.net/YYZZHC999/article/details/88379976

题目:
给定一个非空整数数组,除了某个元素只出现一次以外,其余每个元素均出现两次。找出那个只出现了一次的元素。要求尽量不使用额外空间

示例 1:
输入: [2,2,1]
输出: 1

示例 2:
输入: [4,1,2,1,2]
输出: 4


/**
 * 只出现一次的数字
 * @author 天赋吉运-杨晓慧
 * @create 2019-03-09 21:28
 */
public class singleNumber {

    public static void main(String[] args) {
        int[] nums= {1,1,2,4,2};
        int i = singleNumber(nums);
        System.out.println(i);   // 输出的结果是4
    }

    /**
     * 只出现一次的数字
     * @param nums 传入数组
     * @return 只出现一次的数字
     */
    public static int singleNumber(int[] nums) {

        int x=0;
        for(int i=0;i<nums.length;i++){
            // 按位异或操作
           x=x^nums[i];
        }
        return x;
    }
}

一开始没有任何思路,后来看网友的评论说用java的异或操作可以完美解决这个问题,这才想到把java逻辑运算符练了一把。

    /**
     *java 里的逻辑运算符,与(&)或(|)和异或(^)
     */
    public static void test() {
        int x = 5;
        int y = 11;
        System.out.println(x|y);     // |是按位或--- 输出15
        System.out.println(x&y);     // &是按位与---输出1
        System.out.println(x^y);     // ^是按位异或--- 输出14
    }

过程是这个样子:
x=5 (0101二进制)
y=11(1011二进制)
x|y = 1111 = 15
x&y = 0001 = 1
x^y = 1110 =14


解决这道题主要是用到了异或运算符。

java中异或(用符号XOR或者 ^ 表示)操作的性质了解一下:

1、交换律 a ^ b = b ^a
2、结合律(即(a ^ b) ^ c == a ^ (b ^ c))
3. 任意x,都有x ^ x=0,x ^0=x
4、自反性 A XOR B XOR B = A xor 0 = A

本题的中心思想是这样的:

  • 一个数和自己异或为0
  • 任何一个数和0异或都取本身
  • 所以,一个数和同一个数异或两次之后还是自己. (偶数次都可以,所以本题的题目里备注了是出现两次)

如果重复出现的是奇数次,比如三次或五次,最后的结果一定是所有出现奇数次的数字一起取异或。

举个小例子验证一下这些性质:

4^1 异或 :

0100 (4)

0010 (1)

结果: 0110 (5)

再次与1异或,相当于4^ 1 ^1:

0110 (5)

0010 (1)

结果:0100 (4)

所以一个数与另外一个数异或偶数次之后还等于自己本身,

也换这个角度想: 4^ 1 ^ 1=4 ^ (1 ^ 1)=4^0=4

本题中数组中的4与另外两个数都异或了两次,所以最后异或结果还是4.


以上代码笔者已经过验证,读者阅后可以自行亲测,欢迎交流, 一起写高质量的代码。

猜你喜欢

转载自blog.csdn.net/YYZZHC999/article/details/88379976