在Java中,按位AND,按位包含或问题

时间:2009-02-18 12:59:31

标签: java bit-manipulation byte operator-keyword

我在项目中有几行代码,我看不到......

的价值
buffer[i] = (currentByte & 0x7F) | (currentByte & 0x80);

它从文件中读取文件缓冲区,以字节形式存储,然后传输到缓冲区[i],如图所示,但我无法理解总体目的是什么,有什么想法?

由于

7 个答案:

答案 0 :(得分:9)

正如其他答案所述,(currentByte & 0x7F) | (currentByte & 0x80)相当于(currentByte & 0xFF)。 JLS3 15.22.1表示将其提升为int

  

当操作员和操作员的两个操作数时,   ^,或|是一种类型   convertible(§5.1.8)到原语   积分型,二进制数   促销首先在   操作数(§5.6.2)。的类型   按位运算符表达式是   提升了操作数的类型。

因为JLS3 5.6.2表示当currentByte类型为byte0x7Fint时(情况属实),则两个操作数均为晋升为int

因此,buffer将是元素类型int或更宽的数组。

现在,通过在& 0xFF上执行int,我们有效地将原始byte范围-128..127映射到无符号范围0..255,这是一个经常使用的操作例如java.io个流。

您可以在以下代码段中看到此操作。请注意,要了解此处发生的情况,您必须知道Java将整数类型(char除外)存储为2's complement值。

byte b = -123;
int r = b;
System.out.println(r + "= " + Integer.toBinaryString(r));
int r2 = b & 0xFF;
System.out.println(r2 + "= " + Integer.toBinaryString(r2));

最后,对于一个真实示例,请查看Javadoc并read java.io.ByteArrayInputStream方法的实现:

/**
 * Reads the next byte of data from this input stream. The value 
 * byte is returned as an <code>int</code> in the range 
 * <code>0</code> to <code>255</code>. If no byte is available 
 * because the end of the stream has been reached, the value 
 * <code>-1</code> is returned. 
 */
public synchronized int read() {
return (pos < count) ? (buf[pos++] & 0xff) : -1;
}

答案 1 :(得分:4)

 (currentByte & 0x7F) | (currentByte & 0x80)

相当于

 currentByte & (0x7F | 0x80)

等于

 currentByte & 0xFF

完全相同
 currentByte

编辑:我只看了作业的右侧,我仍然认为等值是真的。

但是,似乎代码想要将有符号字节转换为更大的类型,同时将字节解释为无符号。

在java中有没有更简单的方法将signed-byte转换为unsigned?

答案 2 :(得分:3)

我认为有人在这里做了太多思考。那是不对的。

我只有一句话

  • 原作者担心运行时用本机有符号整数(大概是32位)替换字节,并且明确地试图告诉我们一些关于符号位是“特殊”的东西吗?

这是留下的代码。除非你知道你在一个可疑的运行时间?无论如何,'缓冲'的类型是什么?

答案 3 :(得分:2)

复杂的按位逻辑完全是多余的。

for (int i = 0; i < buffer.length; i++) {
    buffer[i] = filebuffer[currentPosition + i] & 0xff;
}

做同样的事情。如果缓冲区被声明为一个字节数组,你甚至可以省略&amp; 0xff,但遗憾的是没有显示声明。

原因可能是原始开发人员对使用Java签名的字节感到困惑。

答案 4 :(得分:2)

按位AND运算的结果在该位上有一个1,其中两个位都是1,而按位OR运算的结果在这些位上有一个位,其中任何一个位为1。

所以对值0x65的示例评估:

  01100101 0x65
& 01111111 0x7F
===============
  01100101 0x65

  01100101 0x65
& 10000000 0x80
===============
  00000000 0x00

  01100101 0x65
| 00000000 0x00
===============
  01100101 0x65

答案 5 :(得分:0)

关于这些逻辑操作的好处:你可以尝试所有可能的组合(全部256个)并验证你得到了你期望的答案。

答案 6 :(得分:0)

事实证明,正在读取字节的文件采用带符号的位符号,并且长度不同,因此需要执行此任务以允许将其扩展为java int类型,同时保留正确的标志:))