java bit操作_Java位操作及应用

1.概念:​ In digital computer programming, a bitwise operation operates on one or more bit patterns or binary numerals at the level of their individual bits. It is a fast, simple action directly supported by the processor, and is used to manipulate values for comparisons and calculations.

​ On simple low-cost processors, typically, bitwise operations are substantially faster than division, several times faster than multiplication, and sometimes significantly faster than addition. While modern processors usually perform addition and multiplication just as fast as bitwise operations due to their longer instruction pipelines and other architectural design choices, bitwise operations do commonly use less power because of the reduced use of resources.(维基百科)​ 位操作是程序设计中对位模式按位或二进制数的一元和二元操作。在许多古老的微处理器上,位运算比加减运算略快,通常位运算比乘除法运算要快很多。在现代架构中,情况并非如此:位运算的运算速度通常与加法运算相同(仍然快于乘法运算)。

2.操作对象:​ Java位运算是针对于整型类型的二进制进行的移位操作

​ Java整型数据类型有:byte、char、short、int、long

位操作操作的是补码!补码!补码!(重要的事情说三遍)

要把他们转换成二进制形式,必须首先知道他们各占多少字节:数据类型所占位数byte8

boolean8

short16

int32

long64

float32

double64

char16

3.操作符​ Java位操作包括位操作符和移位操作

​ 位操作符包括:&(位与) , |(位或) , ^(位异或) , ~(位非)

​ 位移操作包括:<>(右移) , >>>(无符号右移)

下面简单举例说明一下各种位操作

3.1 &(位与)

4&6

0000 0000 0000 0000 0000 0000 0000 0100

0000 0000 0000 0000 0000 0000 0000 0110

0000 0000 0000 0000 0000 0000 0000 0100

结果:4

再看负数的情况:

-1&6

1000 0000 0000 0000 0000 0000 0000 0001 //-1的原码

1111 1111 1111 1111 1111 1111 1111 1110 //-1的反码

1111 1111 1111 1111 1111 1111 1111 1111 //-1的补码

0000 0000 0000 0000 0000 0000 0000 0110 //6的补码(正数的补码,反码和原码相同)

0000 0000 0000 0000 0000 0000 0000 0110 //计算后的补码(首位为0则是正数,原码与补码相同)

结果:6

3.2 |(位或)

4|6

0000 0000 0000 0000 0000 0000 0000 0100

0000 0000 0000 0000 0000 0000 0000 0110

0000 0000 0000 0000 0000 0000 0000 0110

结果:6

3.3 ^(位异或)

4^6

0000 0000 0000 0000 0000 0000 0000 0100

0000 0000 0000 0000 0000 0000 0000 0110

0000 0000 0000 0000 0000 0000 0000 0010

结果:2

3.4 ~(位非)

~4

0000 0000 0000 0000 0000 0000 0000 0100

1111 1111 1111 1111 1111 1111 1111 1011 //符号位为1,表示负数,所以应该计算原码

1111 1111 1111 1111 1111 1111 1111 1010 //-1获取反码

1000 0000 0000 0000 0000 0000 0000 0101 //原码

结果:-5

3.5 <

位移运算如果位移超过该数据类型表示范围,则先取模,再进行运算(比如针对int型,4>>32等价于4>>0)

2 >> 2

0000 0000 0000 0000 0000 0000 0000 0010

0000 0000 0000 0000 0000 0000 0000 1000 //左移两位

结果:8

3.6 >>(右移)

若正数,高位补0,负数,高位补1

4 >> 2

0000 0000 0000 0000 0000 0000 0000 0100

0000 0000 0000 0000 0000 0000 0000 0001

结果:1

3.7 >>>(无符号右移)

不论正负,高位均补0

-1 >>> 1

1111 1111 1111 1111 1111 1111 1111 1111 //-1补码

0111 1111 1111 1111 1111 1111 1111 1111

结果:2147483647

4.应用场景判断int型变量a是奇数还是偶数

a&1 = 0 偶数

a&1 = 1 奇数求平均值,如果x+y的和会超过int型的值的范围,就可以使用位运算来解决

公式为 (x&y)+((x^y)>>1)

下面简单解释一下:

在二进制进行计算时,x和y的二进制的对应位都有2种情况(相同,不同)。

相同情况下0+0还是0,不用管。1+1需要向前进一位,但是最后会除以2,所以还是原来位置。

不同情况1+0计算结果为1,最后除以2需要右移一位。对于一个大于0的整数,判断它是不是2的n次方

((x&(x-1))==0)&&(x!=0)有两个int类型变量x、y,要求两者数字交换

x ^= y;

y ^= x;

x ^= y;求绝对值

int abs( int x )

{

int y ;

y = x >> 31 ;

return (x^y)-y ; //or: (x+y)^y

}

//如果x为负,其实结果就是对负数求负取模运算

a % (2^n) 等价于 a & (2^n - 1)

//这个在HashMap的原码中用到了,根据key的hash值插入桶中的时候求相反数

~x+1

没有啦,以后遇到一些比较好的位操作使用场景会再来更新

如果发现有什么问题,请联系我更改

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值