Java 中的按位与、按位或或问题
-
05-09-2019 - |
题
我的项目中有几行代码,我看不到它们的价值......
buffer[i] = (currentByte & 0x7F) | (currentByte & 0x80);
它从文件中读取文件缓冲区,存储为字节,然后传输到 buffer[i],如图所示,但我不明白总体目的是什么,有什么想法吗?
谢谢
解决方案
作为其他的答案已经陈述的,(currentByte & 0x7F) | (currentByte & 0x80)
相当于(currentByte & 0xFF)
。该JLS3 15.22.1 说,这是促进到int
:
当操作者的与两个操作数, ^或|是一种类型是的 转换(§5.1.8)为原始 整体式,二进制数字 首先在执行促销 操作数(§5.6.2)。该类型的 位运算符表达是 提升的类型的操作数的
因为JLS3 5.6.2 说当currentByte
具有类型byte
和0x7F
是int
(和是这种情况),那么两个操作数都提升到int
。
因此,buffer
将元素类型int
或更宽的阵列。
现在,通过在执行& 0xFF
int
,我们有效原始byte
范围-128..127映射到无符号范围0..255,经常使用java.io
的操作流例如
您可以在下面的代码片段在行动中看到这一点。需要注意的是要了解这里发生了什么,你要知道,Java的商店组成的类型,除了char
,如 2的补值。
byte b = -123;
int r = b;
System.out.println(r + "= " + Integer.toBinaryString(r));
int r2 = b & 0xFF;
System.out.println(r2 + "= " + Integer.toBinaryString(r2));
最后,对于一个真实的例子,检查出read
的java.io.ByteArrayInputStream
方法的Javadoc和实现:
/**
* 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;
}
其他提示
(currentByte & 0x7F) | (currentByte & 0x80)
等同于
currentByte & (0x7F | 0x80)
其等于
currentByte & 0xFF
这是完全一样的
currentByte
编辑:我只是看着转让的右侧,我仍然认为等效值是真实的。
。然而,它看起来像代码想要的符号字节转换为更大的类型而解释字节为无符号。
有没有签订字节转换为无符号在Java更简单的方法?
我认为有人在这里想太多了。那是不对的。
我只有一点意见
- 原作者担心运行时会用本机有符号整数(大概是 32 位)替换字节,并明确试图告诉我们有关符号位“特殊”的信息?
这是留下的代码。除非你知道自己正处于可疑的运行状态?无论如何,“缓冲区”的类型是什么?
复杂的按位逻辑完全是多余的。
for (int i = 0; i < buffer.length; i++) {
buffer[i] = filebuffer[currentPosition + i] & 0xff;
}
做同样的事情。如果 buffer 被声明为字节数组,您甚至可以省略 & 0xff,但不幸的是该声明没有显示。
原因可能是原始开发人员对 Java 中的字节签名感到困惑。
按位与运算的结果对一个1比特,其中这两个位都为1,而对按位或运算HASE一个的结果位,其中任一机器人的位中的一个是1。
因此,对于一个示例评价的值0x65:
01100101 0x65
& 01111111 0x7F
===============
01100101 0x65
01100101 0x65
& 10000000 0x80
===============
00000000 0x00
01100101 0x65
| 00000000 0x00
===============
01100101 0x65
关于这种类型的逻辑运算的好处:你可以尝试每一个可能的组合(其中所有256),并确认你得到你所期望的答案
原来,其中字节正在从在一个符号位符号读取的文件,并且具有不同的长度,因此它被requried执行此任务,以允许其被扩展到java整数类型,同时保持其正确的符号:)