【问题标题】:Java right shift integer by 32 [duplicate]Java将整数右移32 [重复]
【发布时间】:2021-10-21 11:52:31
【问题描述】:

我试图将一个整数右移 32,但结果是相同的数字。 (例如5 >> 32 是 5。)

如果我尝试对 Byte 和 Short 执行相同的操作,它会起作用。例如,“(byte)5 >> 8”为 0。

整数有什么问题?

【问题讨论】:

  • Byte 是 8 位,short 是 16 位,但它们为什么起作用?
  • @TheLostMind 虽然从 JLS 的角度来看确实如此,但转移与您的评论似乎暗示的轮换不同。
  • @MarkRotteveel 完全同意。 java 包装它的移位量是该语言中一个令人讨厌的错误。 IE。移动 8 位的行为就像移动 32 位,但是移动 64 位突然不同了……他们在抽烟吗?

标签: java bit-manipulation


【解决方案1】:

JLS 15.19. Shift Operators

...如果左侧操作数的提升类型是int,只有右侧操作数的五个最低位用作移位距离。

所以转移32是无效的。

【讨论】:

  • 这是真正的答案。 OP 代码的行为方式(基本上)是因为 Java 语言规范说它必须。
【解决方案2】:

移位转换以int 或long 形式返回结果。所以,即使你转移了一个byte,你也会得到一个int。

Java 代码:

public static void main(String s[]) {
    byte b = 5;
    System.out.println(b >> 8);
    int i = 8;
    System.out.println(i >> 32);
}

字节码:

         0: iconst_5
         1: istore_1
         2: getstatic     #16                 // Field java/lang/System.out:Ljava/io/PrintStream; 
         5: iload_1
         6: bipush        8
         8: ishr
         9: invokevirtual #22      // Method java/io/PrintStream.println:(I)V  ==> Using println(int)
        12: bipush        8
        14: istore_2
        15: getstatic     #16     // Field java/lang/System.out:Ljava/io/PrintStream;
        18: iload_2
        19: bipush        32
        21: ishr
        22: invokevirtual #22      // Method java/io/PrintStream.println:(I)V   ==> Using println(int)
        25: return

【讨论】:

  • @Codebender - 我没说它是循环的
  • 1) 反汇编字节码只对能流利阅读的人有帮助。这可能还不到 Java 程序员的 5%。 2) 它只显示特定编译器生成的内容。谁说编译器是否正确?或者,是否可能存在其他行为不同且“正确”的字节码序列?
  • @StephenC - 尽管有很多反对意见,我还是选择取消删除这个答案,因为字节码在这里提供了有价值的信息。所有的班次都会产生 int 或 long。移动 byte 仍会导致 int。
  • 这是您的意见。我的观点是字节码不能证明任何事情。他们以模糊的方式提供信息。见上面我的cmets。这适用于几乎所有包含反汇编字节码的 Java 问题的答案。这是向人类传达信息的一种非常糟糕的方式,尤其是对于新手 Java 程序员而言。
  • 是的...... JLS 规范是寻求明确答案的正确位置。如果你说字节码转储是一种懒惰的回答方式......我也同意:-)
猜你喜欢
  • 1970-01-01
  • 2013-09-18
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2016-05-07
相关资源
最近更新 更多