我对 JS (ES6) 中的 << 位左运算符的理解是右边的 void 用零填充。
然而,根据经验,我注意到在 V8 和 JSC 中,如果我们移动 64 位或更多,设置的位似乎会突然重新出现。
(255 << 64).toString(2)
//-> "11111111"
这与我的预期相反,即较大的移位将无限期地在右侧仅产生零。
我没有立即在 << 上的 EcmaScript 2016 页面中看到此行为 - 我是否遗漏了什么,或者对于较大的班次,该行为可能未定义?
我对 JS (ES6) 中的 << 位左运算符的理解是右边的 void 用零填充。
然而,根据经验,我注意到在 V8 和 JSC 中,如果我们移动 64 位或更多,设置的位似乎会突然重新出现。
(255 << 64).toString(2)
//-> "11111111"
这与我的预期相反,即较大的移位将无限期地在右侧仅产生零。
我没有立即在 << 上的 EcmaScript 2016 页面中看到此行为 - 我是否遗漏了什么,或者对于较大的班次,该行为可能未定义?
规范(第 12.8.3.1 节)指定要移位的位数被屏蔽:
ShiftExpression:ShiftExpression << AdditiveExpression
- 令 lref 为评估 ShiftExpression 的结果。
- 让 lval 成为
- 获取值(lref)。
- ReturnIfAbrupt(lval)。
- 令 rref 为 AdditiveExpression 求值的结果。
- 设 rval 为 GetValue(rref)。
- ReturnIfAbrupt(rval)。
- 令 lnum 为 ToInt32(lval)。
- ReturnIfAbrupt(lnum)。
- 设 rnum 为 ToUint32(rval)。
- ReturnIfAbrupt(rnum)。
- 令 shiftCount 为屏蔽掉除 rnum 的最低有效 5 位以外的所有结果,即计算 rnum & 0x1F。
- 通过 shiftCount 位返回 lnum 左移的结果。结果是一个有符号的 32 位整数。
由于 64 & 0x1F 为 0,这意味着“没有移位”,这就是位“重新出现”的原因。
要移位的位数上限为 31,即
function shiftLeft(number, numShift) {
return number << (numShift % 32); // equivalent code
}