我不是bitwise运算符的专家,但我经常看到一个模式,在比赛中由256k演示的程序员使用.而不是使用Math.floor()函数,使用双位NOT运算符~~(可能更快?).
像这样:
- Math.floor(2.1); // 2
- ~~2.1 // 2
- 2.1 | 0 // 2
- 2.1 >> 0 // 2
在开发控制台中玩这个时,我注意到了一个我不确定我完全理解的行为.
- Math.floor(2e+21); // 2e+21
- ~~2e+21; // -1119879168
- 2e+21 | 0; // -1119879168
引擎盖下发生了什么?
解决方法
@H_301_19@ 正如Felix King所指出的那样,这些数字正被转换为32位有符号整数. 2e9小于signed int的最大正值,因此这适用:
- ~~(2e9) //2000000000
但是当你转到2e10时,它不能使用所有的位,所以它只需要最低的32位并将其转换为int:
- ~~(2e10) //-1474836480
您可以通过使用另一个按位运算符并确认它正在获取最低32位来验证这一点:
- 2e10 & 0xFFFFFFFF // also -1474836480
- ~~(2e10 & 0xFFFFFFFF) // also -1474836480
Math.floor是为了解释大数而构建的,所以如果大范围内的准确性很重要,那么你应该使用它.
另外值得注意的是:~~正在进行截断,这与仅为正数的地板相同.它不适用于否定:
- Math.floor(-2.1) // -3
- ~~(-2.1) // -2