ByteBuffer是怎么构成的,如何使用?

        ByteBuffer通常用于Java原生NIO操作中,对Channel进行读取或者写入,其中封装了一些操作byte数组的方法,还是很实用的。

ByteBuffer的几个基本属性:

  • position:表示进行下一个读写操作的下标位置

  • limit:表示进行读写操作时的结束位置;

  • capacity:表示存储的容量

  • mark: 对数据进行标记

初始化:对ByteBuffer进行初始化,可以使用静态方法wrap(byte[] data)封装数组,也可以通过另一个静态方法allocate(int size)初始化指定长度的ByteBuffer。

初始状态position:0,limit:值为最大长度,capacity:值为最大长度

 

数据写入(或读取):每写入(或读取)一个值,position加一(图中是写入两个数据之后的位置)。

 

准备读取(或写入):使用flip()方法翻转准备数据读取(或写入),进行读取(或写入)时,不能超过limit限制,读超出限制报错BufferUnderflowException(写超出限制报错BufferOverflowException

 

清除数据:回到初始状态可以调用clear()方法,但是数据并不会删除,当写入时会直接覆盖对应位置的值。

 

标记位置:当需要进行标记时,可以使用mark()方法,即mark=position;进行读取后,可调用reset()方法直接回到mark标记的位置,即position=mark

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
以下是一个可能的实现: ```java import java.io.IOException; import java.io.InputStream; import java.io.OutputStream; import java.nio.ByteBuffer; public class SocketUtil { private static final String HEAD = "BTVRV1"; private static final int HEAD_LENGTH = 6; private static final int TYPE_LENGTH = 2; private static final int LENGTH_LENGTH = 4; private static final int CRC_LENGTH = 4; public static void readFromStream(OutputStream out, InputStream in) throws IOException { ByteBuffer buffer = ByteBuffer.allocate(1024); int bytesRead = in.read(buffer.array(), buffer.position(), buffer.remaining()); if (bytesRead > 0) { buffer.position(buffer.position() + bytesRead); while (buffer.position() >= HEAD_LENGTH + TYPE_LENGTH + LENGTH_LENGTH + CRC_LENGTH) { buffer.flip(); byte[] headBytes = new byte[HEAD_LENGTH]; buffer.get(headBytes); String head = new String(headBytes); if (head.equals(HEAD)) { byte[] typeBytes = new byte[TYPE_LENGTH]; buffer.get(typeBytes); short type = ByteBuffer.wrap(typeBytes).getShort(); byte[] lengthBytes = new byte[LENGTH_LENGTH]; buffer.get(lengthBytes); int length = Integer.reverseBytes(ByteBuffer.wrap(lengthBytes).getInt()); if (buffer.remaining() >= length + CRC_LENGTH) { byte[] dataBytes = new byte[length]; buffer.get(dataBytes); byte[] crcBytes = new byte[CRC_LENGTH]; buffer.get(crcBytes); int crc = Integer.reverseBytes(ByteBuffer.wrap(crcBytes).getInt()); // do something with the data out.write(dataBytes); } else { buffer.compact(); break; } } else { buffer.compact(); break; } buffer.compact(); } } } } ``` 这个实现使用ByteBuffer 来处理输入流中的数据,首先读取尽可能多的数据到缓冲区中,然后循环处理缓冲区中的数据,直到无法再读取出一个完整的数据包为止。对于每个数据包,先读取头部,如果头部不匹配就跳过,否则读取类型、长度、数据和 CRC 值,然后可以对数据进行处理。如果缓冲区中的数据不足以构成一个完整的数据包,就将剩余的数据移到缓冲区的开头,等待下一次读取。
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值