我有这样声明的long
值bits
:
long bits = len*8L;
(304)
System.out.println(bits);
输出为304
如果我像这样使用长名称位,那么我分别得到0和0。
System.out.println(bits>>(4*8));
System.out.println(0xFF&(bits>>(4*8)));
如果我使用实际数字,则分别为304和48
System.out.println(304>>(4*8));
System.out.println(0xFF&(304>>(4*8)));
我正在尝试将此Java转换为JavaScript,但是JavaScript在所有情况下都给我304和48。我需要它来匹配Java并给出0和0的值。
有什么想法吗?
编辑
接下来,为了清楚起见,我需要JavaScript等于0,以模仿Java当前的方式(在等于0之上的两个示例在我们开发的过程中都不会更改)。
因此console.log(0xFF&(bits >>(4 * 8)))应该等于0,当前等于48
答案 0 :(得分:3)
JLS, Section 15.19涵盖了Java中的移位运算符。
如果左侧操作数的提升类型为
int
,则仅将右侧操作数的最低5位用作移位距离。就像右侧操作数受到掩码值0x1f
(0b11111
)的按位逻辑AND运算符&(§15.22.1)一样。因此,实际使用的移位距离始终在0
至31
范围内。
对于诸如int
之类的304
值,4*8
或32的移位值实际上是0
,因此不会发生移位。然后用0xFF
进行和运算,得出48
。
如果左操作数的提升类型为
long
,则仅右操作数的六个最低阶位用作移位距离。就像右侧操作数受到掩码值0x3f
(0b111111
)的按位逻辑AND运算符&(§15.22.1)一样。因此,实际使用的移位距离始终在0
至63
范围内。
对于一个long
值,4*8
的移位值确实确实向右移动了32位,从而产生了0
。
This page涵盖了JavaScript移位运算符。
按位运算符将其操作数视为32位(零和一)的序列,而不是十进制,十六进制或八进制数字。
JavaScript似乎将数字转换为32位数字,例如Java int
。似乎同样的“仅最低5位”规则也适用于JavaScript中的移位操作数。
console.log(304>>32); // Don't shift!
console.log(0xFF&(304>>32)); // Don't shift!
console.log(304>>33); // Shift by 1, not 33
console.log(0xFF&(304>>33)); // Shift by 1, not 33
答案 1 :(得分:0)
如果要在Java中使用常量获得与变量相同的结果,则需要使用304L
将304作为长常量传递,如下所示:
System.out.println(304L>>(4*8));
System.out.println(0xFF&(304L>>(4*8)));
原因是您无法用4 * 8 = 32位移位int
; Java将对32取模32 =零,但是移位,因为int
仅32位长。
相反,JavaScript不支持使用>>
运算符转换64位整数;它将您传递给>>
的每个数字都视为一个32位整数。
您可以编写自己的函数,执行类似的操作:
function rshift(num, bits) {
return Math.round(num / Math.pow(2,bits));
}
console.log(rshift(304, 4*8))