位运算

 位运算

在接触位运算之前,需要先了解十进制转二进制二进制转十进制的转换规则,因为位运算是将其操作数当作32位的比特序列(由0和1组成)进行运算

二进制转十进制

小数点前或者整数要从右到左用二进制的每个数去乘以2的相应次方并递增,小数点后则是从左往右乘以二的相应负次方并递减

示例:

二进制数1101.01转化成十进制

计算公式: 1101.01(2)= 1 * 22 + 0 * 22 + 1 * 22 + 1 * 22 + 0 * 2 -1 + 1 * 2 -2 = 1 + 0 + 4 + 8 + 0 + 0.25 = 13.25(10)

十进制转二进制

采用除2取余,逆序排列法,用2整除十进制整数,可以得到一个商和余数;再用2去除商,又会得到一个商和余数,如此进行,直到商为小于1时为止,然后把先得到的余数作为二进制数的低位有效位,后得到的余数作为二进制数的高位有效位,依次排列起来

javascript中转换方法

js中有内置方法可以直接进行转换,方法如下:

// 二进制字符串
let a = '10010';
// 转十进制
parseInt(a, 2); // 18

// 十进制数
let b = 18;
// 转二进制
b.toString(2); // '10010'

在了解了上面的方法,接下来将介绍在js中按位操作符

运算符 用法 描述
按位与( & )
a & b
对于每一个比特位,只有两个操作数相应的比特位都是1时,结果才为1,否则为0
按位或( | )
a | b
对于每一个比特位,当两个操作数相应的比特位至少有一个1时,结果为1,否则为0
按位异或( ^ )
a ^ b
对于每一个比特位,当两个操作数相应的比特位有且只有一个1时,结果为1,否则为0
按位非( ~ )
~a
反转操作数的比特位,即0变成1,1变成0
左移( << )
a << b
将 a 的二进制形式向左移 b (< 32) 比特位,右边用0填充
有符号右移( >> )
a >> b
将 a 的二进制表示向右移 b (< 32) 位,丢弃被移出的位
无符号右移(>>>)
a >>> b
将 a 的二进制表示向右移 b (< 32) 位,丢弃被移出的位,并使用 0 在左侧填充

按位与( & )

0 & 0 = 0
1 & 1 = 1
0 & 1 = 0

 9 = 00000000000000000000000000001001
 14 = 00000000000000000000000000001110

14 & 9 = 00000000000000000000000000001000 = 8

将任一数值x0执行按位与操作,其结果都为0。将任一数值x-1执行按位与操作,其结果都为x

按位或( | )

0 | 0 = 0
1 | 1 = 1
0 | 1 = 1

 9  = 00000000000000000000000000001001
14  = 00000000000000000000000000001110

14 | 9 = 00000000000000000000000000001111  = 15

将任一数值x0进行按位或操作,其结果都是x。将任一数值x-1 进行按位或操作,其结果都为-1

按位异或( ^ )

0 ^ 0 = 0
1 ^ 1 = 0
0 ^ 1 = 1

 9  = 00000000000000000000000000001001 
14  = 00000000000000000000000000001110 

14 ^ 9 = 00000000000000000000000000000111 = 7

将任一数值x0 进行异或操作,其结果为x。将任一数值x-1 进行异或操作,其结果为 ~x

按位非( ~ )

~1 = 0
~0 = 1

 9  = 00000000000000000000000000001001
 
~9  = 11111111111111111111111111110110  = -10

对任一数值 x 进行按位非操作的结果为 -(x + 1)。例如,~5 结果为 -6

左移( << )

9 = 00000000000000000000000000001001

9 << 2 = 00000000000000000000000000100100 = 36

9 << 2 等价 9 * 2 * 2 = 36
9 << 3 等价 9 * 2 * 2 * 2 = 72

有符号右移( >> )

该操作符会将第一个操作数向右移动指定的位数。向右被移出的位被丢弃,拷贝最左侧的位以填充左侧。由于新的最左侧的位总是和以前相同,符号位没有被改变。所以被称作“符号传播”。

 9 = 00000000000000000000000000001001
 
9 >> 2 = 00000000000000000000000000000010 = 2 

9 >> 2 等价 9 / 2 / 2 = 2
9 >> 3 等价 9 / 2 / 2 / 2 = 1
9 >> 4 等价 9 / 2 / 2 / 2 / 2 = 0

无符号右移(>>>)

该操作符会将第一个操作数向右移动指定的位数。向右被移出的位被丢弃,左侧用0填充。因为符号位变成了 0,所以结果总是非负的

9 = 00000000000000000000000000001001                       
9 >>> 2 = 00000000000000000000000000000010 = 2

-9 = 11111111111111111111111111110111                    
-9 >>> 2 = 00111111111111111111111111111101 = 1073741821

参考文档
Expressions and operators