将无符号字节转换为有符号字节

时间:2011-08-06 11:44:45

标签: java byte unsigned signed

是否有一种简单而优雅的方法可以将无符号字节值转换为java中的有符号字节值?例如,如果我只有int值240(二进制(24位+ 11110000)= 32位),我怎样才能得到这个int的有符号值?

5 个答案:

答案 0 :(得分:25)

在Java中,除char之外的所有原始类型都已签名。你不能有一个无符号字节。 您可以做的唯一事情是将无符号字节转换为int,以便您可以读取其正确的值:

int a = b & 0xff

如果你想在字节类型中存储一个无符号字节值,你显然可以,但每次你需要“处理”它时,只需记住如上所示再次投射它。

答案 1 :(得分:10)

除了char之外,Java没有无符号值。请考虑以下代码段:

byte val = (byte)255;
System.out.println(String.valueOf(val));

结果将为-1,因为最低的8位被复制到字节变量。

答案 2 :(得分:6)

public int getUnsignedByte(byte[] bytes, int offset) {
    return (bytes[offset] & 0xFF);
}

应该做的工作。

答案 3 :(得分:3)

以下是存储和转换无符号字节值的方法:

byte b = (byte) 144; // binary value = 10010000

如果您将b投射到int,请执行以下操作:

int i = b;
System.out.println("value: "+i);  
System.out.println("binary: " + Integer.toBinaryString(i));

输出:

value: -112 <- Incorrect value
binary: 11111111111111111111111110010000 

为什么会这样?字节用Java签名,b为负数,因此强制转换操作从左侧用1s填充结果int。 More on java data formats

那么我们如何从-112回到144的正确值?我们需要一个32位bitmask,我们可以使用int

创建
int mask = 0x000000FF; // This is often shortened to just 0xFF

现在我们可以使用按位&运算符将最左边的24位“清零”,只保留原来的8位。

int unsignedValue = b & mask; // value = 144

我们的原始值144已经恢复,可以安全地返回到一个字节:

byte original = (byte) unsignedValue;

答案 4 :(得分:2)

Java只支持有符号字节,所以无论何时在一个字节中放置一个值,都假定它是带符号的。

byte b = (byte) 240;

但是,如果要存储无符号字节,则需要自己处理。 (即Java不支持它,但你可以这样做)

对于+, - ,*,&lt;&lt;,&gt;&gt;&gt;,==,!=,〜等操作,您无需更改任何内容,对于&lt;,&gt;等操作您需要进行微调,对于像/,%这样的操作,您需要使用更大的数据类型。

一种常见的替代方法是使用较大的数据类型(如int)来存储0到255的值。这样做没有太大的缺点。