标签:简单 ems ima 结合 算法 假设 问题解决 写在前面 str
最近学习不在状态,又遇上期末考试,每年到了这个时候都是最艰难的时候,唉。。。。。。之前就了解过 异或操作 但一直没有形成体系,今天做题又遇到了,想着自己整理一下吧。
异或是一种基于二进制的位运算,用符号XOR或者 ^ 表示,其运算法则是对运算符两侧数的每一个二进制位进行比较,同值取0,异值取1。
1^1=0 0^0=0 1^0=1 0^1=1
例如: 1 ^ 4 = 3 ------->(1) ^ (100) = (101)
1. a ^ b = b ^ a
2. a ^ b ^ c = a ^ (b ^ c) = (a ^ b) ^ c;
3. d = a ^ b ^ c 可以推出 a = d ^ b ^ c.
4. a ^ b ^ a = b.(**这个性质很重要**)
接下来给出几个,我在其他博客上看到的题目,可以帮助更好的去理解异或操作
对于一个有多个数值的数组,只有一个是唯一的,其他都是成对的,怎样快速找到这个唯一值。
如果不了解异或操作的话,估计拿到题目会一脸懵逼中,但这个题目使用异或操作十分简单。(就是使用了这个性质:a ^ b ^ a = b)
//这是一个小例子 int[] num = new int[]{1,2,3,2,3,1,4}; int aim = num[0]; for(int i = 1; i < num.length; i++) { aim = aim ^ num[i]; } System.out.println("最后:"+aim);
由此,问题便可以迎刃而解了。
给你1-1000个连续自然数,然后从中随机去掉两个,再打乱顺序,要求只遍历一次,求出被去掉的两个数。
这个问题,博主给出了两种解决方案:
遍历被打乱的数组时,计算value的累加值和value平方的累加值。结合未打乱之前的数组,这样就能得出
1 x + y = m 2 x*x + y*y = n
两个方程,解这组方程即可算出被去掉的两个数。这种方法比较容易理解,实现起来也比较简单。
首先,这两个数组(打乱前和打乱后)各自异或,也就是1^2^…^1000,得到两个异或值。再对这两个异或值进行一次异或,这样就得到了x^y的指(重复部分互相抵消了)。
// 其实就是把数组的所有元素进行异或,重复部分互相抵消 result = 1^2^...^1000^1^2...^1000; result = 1^1^2^2...^x...^y...^1000^1000; result = x^y;
获取计算出的异或值的1所在的位置,并继续异或
因为x和y是两个不同的整数,所以这两个数的异或结果,转化为二进制的话,一定在某位是1,假设在第3位。也就是说如果把原始数组按第3位是否为0进行划分,就可以分成两个数组,每个数组各包含一个被抽取的数。如果打乱后的数组也按这个规则划分为两个数组,这样就得到了4个数组,其中两组是第3位为0,另外两组是第3位为1。把第3位为0的两个数组所有元素进行异或就能得到被抽取的一个数,同理也就能获得另外一个被抽取的数,于是问题解决
对于二进制串a和b来说,汉明距离等于aXORb中1的数目,我们又称其为汉明权重
public int hammingDistance(int x, int y) { int count = 0; //将x^y转化为二进制数 String ret = Integer.toBinaryString(x ^ y); //统计‘1‘的个数 for(int i = 0;i<ret.length();i++){ if(ret.charAt(i) == ‘1‘) count++; } return count; }
标签:简单 ems ima 结合 算法 假设 问题解决 写在前面 str
原文地址:https://www.cnblogs.com/ANullValue/p/14032321.html