【问题标题】:Java bit shift (lsh) << - error in Java?Java 位移 (lsh) << - Java 中的错误?
【发布时间】:2013-10-24 18:21:42
【问题描述】:

我有一个表情:

short w = (short) ((byte) dana) << x);
...
String.format ("%04X", w);

如果它们包括:

dana = (byte) 0x88;int x = 5;

我收到 0xF100

而不是 0x1100

我该怎么做才能使它正确!

【问题讨论】:

  • 您可以执行按位和 (&amp;) 运算来屏蔽高位。

标签: java bit-manipulation bit-shift


【解决方案1】:

问题出在第一次演员表上:

(byte) dana

dana 被转换为byte,因此当它稍后在表达式中使用时,需要将其扩大回int,这是通过符号扩展来完成的。如果 number 为负数,则所有高位都设置为 1 以保持其值在 2 补码中。

改用位掩码:

short w = (short) ((dana & 0xff) << x);

也许避免使用short 会更好,因为java 无论如何都会对int 进行所有算术运算。

【讨论】:

  • 好的,可以了!谢谢你!但是,如果我应该做一个简短的异或运算呢?即:短计算;计算 ^=w; ???计算 = 计算 & 0xFFFF?
  • @blackmoon,我不太明白。使用 XOR 通常不应该与更高位混淆。如果您想在没有符号扩展的情况下将short 扩大到int,那么&amp; 0xFFFF 是一个不错的选择。但是当分配给short 时,这是毫无意义的。
  • 我应该在 C++ 中计算 CRC ...:short CalcCrc(char *str,int len) { short crc=0; for(int i=0;i&lt;len;i++) crc ^= (short)((unsigned char)str[i]) &lt;&lt; (i%9); return crc; } 但在 Java 中并不总是相同的(如果我使用相同的字符串)
  • @blackmoon,我认为用0xff &amp; 替换(unsigned char) 就足够了。在这种情况下,将 short crc 更改为 int 并删除 (short) 也不应该有太大变化,因为您永远不会设置高位。
【解决方案2】:

检查这个答案:How to cast from int to byte, then use a bitshift operator

你以(扩展符号)开头

  1111 1111 1111 1111 1111 1111 1000 1000

然后换班

  1111 1111 1111 1111 1111 0001 0000 0000

当你转换为short时,你以

结尾
  1111 0001 0000 0000

你得到的结果是什么。

解决方案是使用更宽的值(至少short),所以它不会是负数。 zch的回答也是有效的。

【讨论】:

    【解决方案3】:

    您可以执行按位和 (&) 操作来屏蔽高位。例如:

    w &= 0x1fff;
    

    问题在于,当将数据转换为字节时,符号位被激活并执行算术运算而不是逻辑运算。通过使用 nd 操作,高位被切断。或者,您可以推迟转换并将其作为后处理。

    有时也可以使用算术移位

    【讨论】:

    • 你不是在解释一个解决方案,而是一个补丁。执行w = 0x1100 也可以得到预期的结果,但这也不是解决方案。
    • 什么是“算术移位”? &lt;&lt;&gt;&gt;有符号移位&gt;&gt;&gt;无符号移位(并且只能在相反方向工作,没有&lt;&lt;&lt;
    • 有些语言提供旋转,有些人也将其归类为算术移位。我知道范围是Java,但是如果一个人想学习编程,他应该看到大局,而不仅仅是一种编程语言的实现......
    猜你喜欢
    • 1970-01-01
    • 2011-04-23
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多