JS位运算实用价值

253 阅读4分钟

本文已参与「掘力星计划」,赢取创作大礼包,挑战创作激励金。


关于位运算的基础知识

JavaScript 位运算符

运算符名称描述
&AND如果两位都是 1 则设置每位为 1
image.pngOR如果两位之一为 1 则设置每位为 1
XOR如果两位只有一位为 1 则设置每位为 1
~NOT反转所有位
<<零填充左位移通过从右推入零向左位移,并使最左边的位脱落。
>>有符号右位移通过从左推入最左位的拷贝来向右位移,并使最右边的位脱落。
>>>零填充右位移通过从左推入零来向右位移,并使最右边的位脱落。

实例

操作结果等同于结果
5 & 110101 & 00010001
5 image.png 15010100010101
5 ^ 140101 ^ 00010100
~ 510~01011010
5 << 1100101 << 11010
5 >> 120101 >> 10010
5 >>> 120101 >>> 10010

详细的可以去w3c看看www.w3school.com.cn/js/js_bitwi…

干货在此

按位非 ~

按位非的最终结果始终是对原数值取反并减一

使用按位非 ~ 判断是否等于-1

按位非的写法来校验 -1 ,
`indexOf` 方法在找不到相同值时返回 -1,
而 ~-1 == 0 == false,
所以 !~-1 == 1 == true

使用按位非 ~ 取整

位运算双非取整

 ~~3.14 == 3JS 位运算中,并不会用 64 位来计算,它会先在后台把值转换为 32 位整数,再进行位运算操作,
位运算计算完成后再将 32 位转为 64 位存储,整个过程就像在处理 32 位数值一样

所以位运算中的双非 `~~` 即可取整,此取整是完全忽略小数部分

按位与 &

按位与操作符也就是符号 `&` ,它有两个操作数,其实就是将两个操作数的二进制每一位进行对比,
两个操作数相应的位都为 1 时,结果为 1,否则都为 0

使用按位与 & 判断奇偶数

偶数 & 1  //0   
奇数 & 1   // 1

按位或 OR(|)

按位或用符号 `|` 来表示,它也有两个操作数,按位或也是将两个操作数二进制的每一位进行对比,
只不过按位或是两边只要有一个 1 ,结果就是 1,只有两边都是 0 ,结果才为 0

使用按位或 | 取整

1.111 | 0  //  1
12.234 | 0 //  12

只需要将小数同 0 进行按位或运算即可

使用按位或 | 代替Math.round()

四舍五入
12.1 | 0 // 12

按位异或 XOR(^)

异或的运算过程可以当作把两个数加起来,然后进位去掉

相同抵消留下不同
1^2^3^4^5 // 1   

使用按位异或 ^ 判断整数部分是否相等

let a = 1
let b = 1
a ^ b // 0 
1 ^ 1 // 0 
2 ^ 2 // 0
3 ^ 3 // 0

使用按位异或 ^ 来完成值交换

// 如果a ^ b = c
// 那么c ^ b = ac ^ a = b

不如用 ES6 的解构

使用按位异或 ^ 切换 0 和 1

let toggle = 0
toggle ^= 1

原理也简单, `toggle ^= 1` 等同于 `toggle = toggle ^ 1`,我们知道 `0 ^ 1` 等于 1,而 `1 ^ 1` 则为 0

使用按位异或 ^ 判断两数符号是否相同

`(a ^ b) >= 0` 来判断两个数字符号是否相同,也就是说同为正或同为负

左移(<<)

x <<y  // 等同于 x * 2^y

使用左移 << 取整

1.111 <<0  // 1
2.944 <<0  // 2

有符号右移(>>)

x >> y  // 等同于x / 2^y*

使用右移 >> 取整

1.111 >> 0  // 1
2.944 >> 0 // 2

无符号右移(>>>)

正数取整
1.323 >>> 0 // 1
2.924 >>> 0 // 2

用的不多 , 但是也得了解 .

位运算概念

位运算是在数字底层(即表示数字的 32 个数位)进行运算的。由于位运算是低级的运算操作,所以速度往往也是最快的(相对其它运算如加减乘除来说),并且借助位运算有时我们还能实现更简单的程序逻辑,缺点是很不直观,许多场合不能够使用。

「欢迎在评论区讨论,掘金官方将在掘力星计划活动结束后,在评论区抽送100份掘金周边,抽奖详情见活动文章」