在JavaNIO中使用ByteBuffer读写Int

在JavaNIO中使用ByteBuffer读写Int,java,networking,nio,bytebuffer,data-conversion,Java,Networking,Nio,Bytebuffer,Data Conversion,我想使用JavaNIOAPI中的数据报通道在网络上传输一个int数组。但是,函数读/写只能将字节缓冲作为输入。所以我需要将int数据存储到一个字节缓冲区,然后在接收器上读回。我面临的是java.nio.BufferUnderflowException。以下是我在发送方所做的工作: for(i = 0; i < send_data.length; i++) { //Write the data onto Buffer ByteBuffer buffer

我想使用JavaNIOAPI中的数据报通道在网络上传输一个int数组。但是,函数读/写只能将
字节缓冲
作为输入。所以我需要将int数据存储到一个
字节缓冲区
,然后在接收器上读回。我面临的是
java.nio.BufferUnderflowException
。以下是我在发送方所做的工作:

for(i = 0; i < send_data.length; i++)
{
          //Write the data onto Buffer
          ByteBuffer buffer1 = ByteBuffer.allocate(send_data[i].length*4);
          for(j = 0; j < send_data[i].length; j++)
                     buffer1.putInt(send_data[i][j]);
          buffer1.flip();
          //Transmit the data
          while(buffer1.hasRemaining())
                 channel.write(buffer1);
}
类似地,
recvpkt
是一个2D数组,它的每一行将从网络接收一个数据包

我读到
getInt()
ByteBuffer
读取4个字节,并将当前位置移动4个字节。是因为我错误地使用了
buffer.flip()
。我不熟悉使用
NIO
,在如何调试这些问题上遇到了困难

更新:

错误不再发生。但是现在接收器得到的都是零。而我在每个包中传输一个二进制序列。当我从发送方本身的缓冲区读取时,所有条目都正确显示,但在接收方接收到的缓冲区都是零。不知道为什么会这样

更新2:

最后,经过数小时的努力,问题终于解决了。当你收到缓冲区时,你需要倒带它

  channel.receive(buffer);
  buffer.rewind();
如果现在在缓冲区上使用getInt方法,您将能够成功读取缓冲区。

每次从写入切换到读取以及从读取切换到写入时,您都有一个翻转()缓冲区。将flip()添加到
receive()之后的第二个示例中


一旦你完成了这项工作,你应该看看如何重新使用你的ByteBuffers,EJP建议。

这几乎是你所能做到的最低效的。您应该分配一个ByteBuffer,存储其中的所有数据,然后使用写入循环发送所有数据。。但目前我想了解为什么我会得到上述异常。我的意思是,除了效率,我的代码有什么问题吗?flip将缓冲区的当前位置设置为其限制,当前位置设置为0。在接收端再次翻转不会导致问题吗?我的意思是,我一次将数据包写入缓冲区,翻转缓冲区,然后读取它。那么,为什么在读取时会再次发生翻转呢?在这两种情况下,您都会写入缓冲区,并且位置具有写入到的点。然后你需要从开始读到写下的那一点。这两个例子之间的唯一区别是谁写谁读,但在这两种情况下,你都需要在两者之间进行转换。尽管名称(愚蠢),flip()并不是其本身的反义词。在写入或获取之前必须翻转,之后必须压缩()或清除()。如果压缩()或清除(),则不需要翻转(),也不需要翻转()。不,不需要。这不是可逆操作。更正确的说法是,flip()为写入或获取缓冲区做好准备,compact()和clear()为读取或放入缓冲区做好准备。如果您只是使用flip()而不是compact()或clear(),它就不起作用。
  channel.receive(buffer);
  buffer.rewind();