题目一:不用额外的变量去使得两个数交换。
a = a ^ b;
b = a ^ b;
a = a ^ b;
题目二:一个数组中有一种数出现了奇数次,其他数都出现了偶数次,怎么找到并打印这种数
public static void main(String[] args) {
int[] b = {1, 8, 9, 3, 1, 8, 9, 3, 9, 6, 6};
System.out.println(findOddNum(b));
}
public static int findOddNum(int[] arr) {
// 验证数据是否可靠
if (arr == null || arr.length == 0 ){
return -1;
}
int temp = 0;
for (int ele : arr) {
temp ^= ele;
}
return temp;
}
测试运算结果:
题目三:怎么把一个int类型的数,提取出最右侧的1来
利用算法:N & (~N + 1)
public static void main(String[] args) {
int[] a = {1, 2, 4, 3, 5, 6};
int[] b = {1, 8, 9, 3, 0, 6};
int c = 6;
System.out.println(getLastOne(c));
}
public static int getLastOne(int num) {
return num & (~num + 1);
}
题目四:一个数组中有两种数出现了奇数次,其他数都出现了偶数次,怎么 找到并打印这两种数
public static void printOddTimesNum2(int[] arr){//只有两个数出现了奇数次
int eor=0;
for(int cur:arr){
eor^=cur;
}
//eor=a^b
//eor!=0
//eor必然有一个位置上是1
// 0110010000
// 0000010000 【小算法】
int rightOne=eor&(~eor+1);//提取出最右的1
int eorT=0;//eor'
for(int cur:arr){
if((cur&rightOne)==1){
eorT^=cur;
}
}
System.out.println(eorT+" "+(eor^eorT));
}
思路:
实际例子:
计算一个二进制数中有几个1?
int count = 0;
while ( n != 0 ) {
right = n & ( ~n + 1 );
count++;
n ^= right; //抹去最右边的1
}