您现在的位置是:首页 > 文章详情

Java 中的位运算

日期:2018-08-20点击:284

预备知识

原码 : 符号位加上真值的绝对值, 即用第一位表示符号, 其余位表示值。

反码 : 正数的反码是其本身;负数的反码是在其原码的基础上, 符号位不变,其余各个位取反。

补码 :
在计算机中,二进制数值是以补码的形式存放, 正数补码是其本身,负数的补码为 除符号位的(反码+1)

计算机中的数值是以其补码的方式存储的.

java中的基础位运算符

java中提供的基础位运算符有 与(&),或(|),非(~),异或(^),左移<<,
右移(>>)无符号右移(>>>).

除了位非(~)是一元操作符外,其它的都是二元操作符。

以下的 A,B为二进制表示的数字.

按位与

A & B : A和B对应的二进制数位都为1时,结果才为1,其他情况为0.

A = 001101 // 13 B = 100101 // 37 A & B = 000101 // 5 

按位或

A | B : A和B对应的二进制数位都为0时,结果才为0,其他情况为1.

A = 001101 // 13 B = 100101 // 37 A | B = 101101 // 45 

按位非

~A : 将a的二进制表示每一位进行取反操作,0变1,1变0.
相当于相反数 - 1

A = 001101 // 13 ~A = 11111111111111111111111111110010 // 32位,补码表示,第一位为符号位 // 根据上诉补码转原码为 // 10000000000000000000000000001110 // -14 

按位异或

A ^ B:将A和B对应的二进制位不同,结果位为1,否则为0。

A = 001101 // 13 B = 100101 // 37 A | B = 101000 // 40 

左移操作

A << B:将A的二进制表示的每一位向左移B位,左边超出的位截掉,右边不足的位补0。
在取值范围内,移动一位相当于乘2.

A = 001101 // 13 A << 1 = 011010 // 26 

右移操作

A >> B: 是带符号右移,若左操作数是正数,则高位补“0”,若左操作数是负数,则高位补“1”.
在取值范围内,移动一位相当于除2.

A = 001101 // 13 A >> 1 = 000110 // 6 

无符号右移操作

A >>> B: 是无符号右移,无论左操作数是正数还是负数,在高位都补“0”
在取值范围内,正数移动一位相当于除2.

A = 11111111111111111111111111110011 // -13 A >>> 1 = 01111111111111111111111111111001 // 2147483641 

位运算例子

  1. 根据 A ^ A = 0的特性,完成数值交换
int a = 2; int b = 3; a = a ^ b; b = a ^ b; a = a ^ b; System.out.println(a); // 3 System.out.println(b); // 2 
  1. 整型字符的 乘 2 ^ n 或者 除 2 ^ n
A = 001101 // 13 A >> 1 = 000110 // 相当于 13 / 2 
  1. 判断一个数的奇偶性

最后二进制最后一位是1为奇数,为0是偶数.

 boolean isOddNumber(int n){ return (n & 1) == 1; } 
  1. A ^ -1 相当 ~A.

  2. 求相反数

 int oppositeNumber(int num) { return ~num + 1; } 
  1. 求绝对值
 /** * n>>31 取决于n的符号,若n为正数,n>>31等于0,若n为负数,n>>31等于-1 * 负数时,相当于 (n ^ -1) + 1 */ int abs(int n) { return (n ^ (n >> 31)) - (n >> 31); } 
  1. 求最大值
 /** * b & -1 == b * ~0 == -1 */ int max(int a, int b) { return b & ((a - b) >> 31) | a & (~(a - b) >> 31); } 
  1. 求最小值
 /** * b & -1 == b * ~0 == -1 */ int max(int a, int b) { return a & ((a - b) >> 31) | b & (~(a - b) >> 31); } 
  1. 判断符号相同
 /** * 有 0 时,方法不成立. * @return true 表示 x和y有相同的符号, false表示x,y有相反的符号。 */ boolean isSameSign(int x, int y) { return (x ^ y) >= 0; } 
  1. 取平均值
 int average(int x, int y) { return (x + y) >> 1; } 
原文链接:https://yq.aliyun.com/articles/666854
关注公众号

低调大师中文资讯倾力打造互联网数据资讯、行业资源、电子商务、移动互联网、网络营销平台。

持续更新报道IT业界、互联网、市场资讯、驱动更新,是最及时权威的产业资讯及硬件资讯报道平台。

转载内容版权归作者及来源网站所有,本站原创内容转载请注明来源。

文章评论

共有0条评论来说两句吧...

文章二维码

扫描即可查看该文章

点击排行

推荐阅读

最新文章