通过网络写入 4 字节的无符号整数

发布于 2024-12-10 15:09:49 字数 1018 浏览 0 评论 0原文

我在 java 中编写无符号 4 字节 int 时遇到问题。

在 java 中写入 long 值在 64 位 MacOS 和 32 位 Linux (Ubuntu) 上都会有不同的结果 或者 向网络写入 4 字节无符号整数有问题。

以下调用在我的本地 OSX 上完美运行

writeUInt32(999999,outputstream)

读回它给我 999999

但是,当应用程序部署到网络时,写入一个长值会导致一些其他随机数(我假设字节序已被切换?)并且读取它给我一些其他大量。

---------- 完整的方法堆栈如下 --------------

public void writeUInt32(long uint32,DataOutputStream stream) throws IOException {
        writeUInt16((int) (uint32 & 0xffff0000) >> 16,stream);
        writeUInt16((int) uint32 & 0x0000ffff,stream);
    }

public void writeUInt16(int uint16,DataOutputStream stream) throws IOException {
        writeUInt8(uint16 >> 8, stream);
        writeUInt8(uint16, stream);
    }

public void writeUInt8(int uint8,DataOutputStream stream) throws IOException {
        stream.write(uint8 & 0xFF);
    }

编辑:添加到写入文件然后通过网络传输的混乱向我发送正确的值!因此,当outputstream指向本地文件时,它会写入正确的值,但是当outputstream指向ByteArrayOutputStream时,写入的long值是错误的。

I have problem writing an unsigned 4 bytes int in java.

Either writing a long value in java has different result on 64 bit MacOS and 32 bit Linux (Ubuntu)
OR
Writing to network a 4 byte unsigned int has a problem.

The following call works perfectly on my local OSX

writeUInt32(999999,outputstream)

Reading it back gives me 999999

However when the application is deployed to a network writing a long value results in some other random number (I assume the endian has been switched?) and reading it gives me some other large number.

---------- The complete method stack is as below---------------

public void writeUInt32(long uint32,DataOutputStream stream) throws IOException {
        writeUInt16((int) (uint32 & 0xffff0000) >> 16,stream);
        writeUInt16((int) uint32 & 0x0000ffff,stream);
    }

public void writeUInt16(int uint16,DataOutputStream stream) throws IOException {
        writeUInt8(uint16 >> 8, stream);
        writeUInt8(uint16, stream);
    }

public void writeUInt8(int uint8,DataOutputStream stream) throws IOException {
        stream.write(uint8 & 0xFF);
    }

Edit: To add to the confusion writing to a file and then transporting it over the network sends me the correct value! So when outputstream points to a local file then it writes the correct values but when outputstream points to a ByteArrayOutputStream then the long value written is wrong.

如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

扫码二维码加入Web技术交流群

发布评论

需要 登录 才能够评论, 你可以免费 注册 一个本站的账号。

评论(1

冷︶言冷语的世界 2024-12-17 15:09:49

只需使用数据输出/输入流。

要写入,请将 long 转换为 int

public void writeUInt32(
      long uint32,
      DataOutputStream stream
    ) throws IOException
{
    stream.writeInt( (int) uint32 );
}

在读取时,使用 readInt,分配给 long 并屏蔽前 32 位以获得无符号值。

public long readUInt32(
      DataInputStream stream
    ) throws IOException
{
    long retVal = stream.readInt( );

    return retVal & 0x00000000FFFFFFFFL;
}

编辑

从您的问题来看,您似乎对原始类型的 Java 强制转换和升级感到困惑。

请阅读 Java 规范中有关转换和升级的部分:http:// java.sun.com/docs/books/jls/third_edition/html/conversions.html

Just use DataOutput/InputStream.

To write, cast your long to int

public void writeUInt32(
      long uint32,
      DataOutputStream stream
    ) throws IOException
{
    stream.writeInt( (int) uint32 );
}

On read, use readInt, assign to long and mask top 32 bits to get unsigned value.

public long readUInt32(
      DataInputStream stream
    ) throws IOException
{
    long retVal = stream.readInt( );

    return retVal & 0x00000000FFFFFFFFL;
}

EDIT

From your questions, looks like you are confused about Java cast conversions and promotions for primitive types.

Read this section of Java Spec on Conversions and Promotions: http://java.sun.com/docs/books/jls/third_edition/html/conversions.html

~没有更多了~
我们使用 Cookies 和其他技术来定制您的体验包括您的登录状态等。通过阅读我们的 隐私政策 了解更多相关信息。 单击 接受 或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。
原文