1

以下代码(这是一个简化版本)用于在 jdk1.6 中运行良好,现在断言在 jdk 1.7 下失败。

ByteBuffer buffer = ...;
buffer.mark();
char c = (char) buffer.get();
buffer.reset();

switch(c) {
  ...
  case 'H':
    byte b = buffer.get(); 
    //Here I get -106 for b and 72 for (byte) c
    assert( b == ((byte) c) );
    break;
  ...
}

我阅读了oracle 的兼容性页面,但没有找到任何可以解释的内容。也许是 utf8 的 5 和 6 形式,但我不认为是这样。这也可能是我仍在调查的竞争条件,但我认为询问 stackoverflow 不会有什么坏处:-)

4

3 回答 3

2

不,行为没有从 1.6 更改为 1.7——或者,就此而言,从 1.0 更改为 1.7。

当你执行这行代码时:

char c = (char) buffer.get();

您正在有效地执行以下步骤:

  1. byte从缓冲区中检索一个值
  2. 将该值转换为int. 负值以二进制补码形式表示。
  3. 将该整数转换为char. 这将简单地屏蔽高位两个字节,因此二进制补码整数将是一个“大”字符值。

在您的情况下,可能发生的是数据格式已更改,因此您不在预期的位置。查看代码的其余部分,您正在阅读的“字符”似乎应该是简单的 ASCII 值。

于 2013-05-16T15:45:15.737 回答
1

byte 的值范围从 -128 到 +127(8 位有符号) char 的值范围从 0 到 +65535(16 位无符号) 如果你不将“c”转换为 char 它可以工作。

于 2013-05-16T14:52:35.187 回答
0

对的,这是可能的。字符范围是 0 到 65535,字节范围是 -128 到 127。所以

如果您将小于 0 的字节转换为 char,您将得到错误的数据

如果你将 smth 从 -128 投射到 127 到 byte 你会得到错误的值

于 2013-05-16T14:58:27.503 回答