【js位运算】 零填充右移运算>>>

358 阅读2分钟

js中的位运算执行效率更高,恰当地使用可以使代码更加优雅,性能更高。本文以零填充右移运算>>>为切入点,整理一下js位运算。

js中的位运算基于32位二进制数执行

js中数字是以64位浮点数形式存储的,默认为十进制。在执行位运算之前,js将数字转换为32位有符号整数,执行完位运算后,再将数值转换为64位十进制数字。 image.png 上图是js中执行位运算的大致流程,可以看到补码是用于位运算的,位运算结束后的结果仍是补码,需要转成原码表示数值

怎样求数字的二进制补码?

先来了解几个概念:

  1. 原码 如图所示最高位(蓝色)是符号位,0表示正数1表示负数。其他位(白色)表示数值。 image.png
  2. 反码

1)正数的反码

正数本身,即原码。

2)负数的反码

符号位不变,其余位取反。

image.png 3. 补码

求补码的方法:

1) 正数的补码是本身,即原码。

2) 负数的补码是负数的反码加1.

image.png

4.补码转原码

1) 补码为正数,原码是本身。

2) 补码为负数,原码是补码-1的反码.

image.png

零填充右移运算>>>

下面通过两个🌰理解一下>>>运算。

例1: 正数零填充右移

let num = 5;
// 转二进制
num.toString(2); // '101'
num = num >>> 1; // 2
num.toString(2); // '10'

5的二进制表示为101,执行5 >>> 1,即将5的二进制表示右移1位,空出来的高位用0填充。

image.png 如图所示,5的补码是5,右移1位高位补0得到2,2转成原码还是2.

注意: 符号位也参与了运算!

例2: 负数零填充右移

let num = -5;
// 转二进制
num.toString(2); // '-101'
num = num >>> 1; // 2147483645
num.toString(2); // '1111111111111111111111111111101'

image.png 如图所示,-5的二进制补码是11111111111111111111111111111011,右移1位高位补0得到01111111111111111111111111111101,由负数变成了正数,原码是正数本身,即2147483645。

由于右移后高位补0,所以零填充右移的结果恒为非负值。

总结

  1. js中会将数值转成对应的二进制补码,再执行位运算,运算结束后,将结果转换成原码表示数值。
  2. 零填充右移运算>>>,符号位也参与运算,零填充右移的结果恒为非负值。

参考文档

1.JavaScript 位运算符