- 今天重温的主要是Java运算符,在这里我把之前已经遗忘的一些点记录下来,以后回顾的时候可以翻阅。
比较运算符
^异或:
- 符号两边的结果相同为False,不同则为True1 
 2
 3
 4True ^ True = False ; 
 False ^ True = True ;
 True ^ False = True ;
 False ^ False = False ;
!非:
- 两次非运算就是原数1 
 2!true = false ; 
 !!true = true ;
逻辑运算符
&和&&的区别:
- 让我们先来看一段代码 - 1 
 2
 3- int x = 1; 
 if(x>2 && x<5)
 System.out.println();
- 在上面的情况中,在对 && 左边的式子进行判断后,得出左边的式子值是false,因为两数相与,只要有一个flase,整体式子的结果就是false。所以停止运算右侧式子,直接给出false的结果。 
- 但是使用 & 运算符的时候,无论左边式子是什么,右边都参与运算。 
- && 和 & 运算结果一样,过程有一些小区别 
 & :无论左边式子是什么,右边都参与运算
 && :当式子左边为false时,右边不参与运算,结果为false
|和||的区别
- 上面我们说了 & 和 && 的区别,其实原理是一样的
- || 和 | 运算结果一样,过程有一些小区别
 | :无论左边式子是什么,右边都参与运算
 || :当式子左边为true时,右边不参与运算,结果为true
位运算
& 位运算
- 下面我用一个小例子来演示 - 1 
 2
 3
 4
 5
 6
 7- 6 & 3 = ? 
 内存中
 0000-0000 0000-0000 0000-0000 0000-0110
 & 0000-0000 0000-0000 0000-0000 0000-0011
 -----------------------------------------
 0000-0000 0000-0000 0000-0000 0000-0010
 ∴ 6 & 3 = 2
- 6 & 3 在内存中变化的实质是,转换为2进制,各位相对应的进行 & 运算 
- 应用场景: 
 取0100 0000 1100 0101的后四位,如何进行操作?
 答 :用0000 0000 0000 1111与其进行 & 运算。
| 位运算
- 原理同上 例如 6 | 3 = 7
^ 位运算
- 原理同上 - 1 
 2
 3
 4
 5
 6
 7
 8
 9
 10
 11
 12- 6 ^ 3 = ? 
 内存中(简化)
 0110
 ^ 0011
 ------
 0101
 ∴ 6 ^ 3 = 5
 继续 ^ 3
 5 ^ 3 = ?
 演算后
 5 ^ 3 = 6
- 不知道大家发没发现这个运算的一些小秘密,那就是一个数连续两次与相同的数进行异或运算后,结果会是最初的数。用公式写就是: a ^ b ^ b = a 
- 那么这个究竟可以用作干什么那?可以用于文件的加密!
~ 反码
- 大家可以在自己的电脑上试一下下面的代码,看看是不是自己猜测的值 - 1 
 2- int a = 2; 
 System.out.println(~a);
- 结果是 -3 ,很多人可能都以为反码的意思就是将a的二进制10取反为01,猜测结果是1 
- 为什么不是这样的运算过程那?
原理
这就要从计算机常用的几个码说起了。首先,java存储的是有符号数,在计算机中,有符号数通常是使用补码存储的,java也不例外。先来看看什么叫原码,反码,补码。
原码
原码就是符号位加上真值的绝对值,即用第一位表示符号, 其余位表示值. 比如如果是8位二进制:1
[+1]原 = 0000 0001
反码
正数的反码是其本身
负数的反码是在其原码的基础上,符号位不变,其余各个位取反.
例如:1
[+1] = [00000001]原 = [00000001]反
补码
正数的补码就是其本身
负数的补码是在反码的基础上+1。
例如:1
[+1] = [00000001]原 = [00000001]反 = [00000001]补
分析
所以回到一开始的问题,int a = 2 a在计算机中是以补码存储的。
- 对于2这个正数来说,补码、反码、原码都是相同的,又由于是数值型,在这里我先用八位bit来表示一下:1 
 2原码:0000 0010 
 反码:0000 0010
补码:0000 0010
- 取反 
 取反过程是在补码的基础上进行的,由于是按位取反,无论符号位还是数值位都要取反,所以结果如下:- 1 - 取反后的补码: 1111 1101 
- 换算为值 
 那么取反后的补码的实际值是多少呢?我们需要先把他转化为原码,过程如下:- 1 - 反码 = 1111 1101 - 1 = 1111 1100 
原码 = 反码符号位不变,其余取反 = 1000 0011
所以,最后的值-3
<< 左移
- 这个符号之前并没有听说过,在这次学习中进行了掌握(开始我还以为是C++的cout那) - 1 
 2
 3
 4
 5
 6- 3 << 2 = ? 
 内存中
 0000-0000 0000-0000 0000-0000 0000-0011
 结果
 0000-0000 0000-0000 0000-0000 0000-1100
 ∴ 3 << 2 = 12
- 上面的运算实质是 3的2进制 整题左移两位,多余的舍弃,空位用0补 
- 一个数进行左移运算时,左移n位,即是该数乘以2的n次幂
>> 右移
- 原理几乎一样,只有略微的不同
 原来最高位是什么,用什么补空位(因为最高位为1时是负数)
- 右移n位,即是该数除以2的n次幂1 
 2
 3
 4-12 >> 2 = ? 
 答: -3
 12 >> 2 = ?
 答: 3
>>> 无符号右移
- 高位空位,全部填0,用0补位1 
 2
 3
 4-12 >>> 2 = ? 
 答: 3
 12 >>> 2 = ?
 答: 3
应用
- 请用效率最高的方法求出 2*8 的值。 - 1 - System.out.println(2<<3); 
- 两个整数值互换(不使用第三方变量) - 1 
 2
 3
 4
 5
 6
 7
 8
 9
 10
 11- 方法1:(不建议使用,如果数值过大,可能丢失精度) 
 int a = 3, b = 5;
 a = a + b;
 b = a - b;
 a = a - b
 方法2:(利用异或位运算)
 int a = 3, b = 5;
 a = a ^ b;
 b = a ^ b;
 a = a ^ b;
三元运算符
- (条件表达式)?表达式1:表达式2
- 若条件为true ,结果为表达式1
 若条件为false,结果为表达式21 
 2
 3
 4练习:在x , y中取 值较大的整数 
 int x = 3, y = 4;
 int max = ( x>y )? x : y;
 System.out.println(max);
swich 和 if else 与 三元运算符
- 三元运算符必须有结果,if else可有,可不有结果。当if else有具体运算结果时,可以使用三元运算符。 - 1 
 2
 3
 4
 5
 6
 7
 8
 9
 10
 11
 12
 13
 14
 15
 16
 17- swich使用示范: 
 int x = 3;
 swich(x)
 {
 case 1:
 System.out.println(x);
 break;
 case 2:
 System.out.println(x);
 break;
 case 3:
 System.out.println(x);
 break;
 case default:
 System.out.println(x);
 break;
 }
- if: - 对几个具体值进行判断 对区间判断 对运算结果boolean类型表达式判断- swich: - 对几个具体值进行判断 值的个数通常是固定的
- 对几个固定值判断,建议使用swich,swich将答案存在内存中,效率高