Java 网络编程之NIO(ByteBuffer)

    

在 Java NIO 中,ByteBuffer 是用于存储和传输数据的一种数据结构。它提供了高效的数据存储和读取能力,使得 Java NIO 能够高效地处理大量的数据输入输出。

ByteBuffer 的作用包括以下几个方面:

  1. 存储数据:ByteBuffer 可以存储任意长度的数据,可以根据需要动态地分配内存空间。通过 wrap() 方法可以将 ByteBuffer 包装成一个 Java ByteBuffer 对象,使得它可以被序列化和反序列化。

  2. 读取数据:ByteBuffer 提供了 read() 方法来读取数据,可以读取任意长度的数据,并且可以异步读取。read() 方法返回实际读取的数据长度,如果读取失败,则返回 -1。

  3. 写入数据:ByteBuffer 提供了 put() 方法来写入数据,可以异步写入数据。put() 方法将数据写入到 ByteBuffer 中,并将其标记为已填充。在写入数据后,可以使用 flush() 方法将数据写入到目的地。

  4. 连接数据:ByteBuffer 提供了连接数据的功能。通过连接数据,可以将多个数据包组合成一个数据包进行传输。连接数据可以提高数据传输的效率,减少数据传输的延迟。

总之,ByteBuffer 是 Java NIO 中的核心数据结构,它提供了高效的数据存储和读取能力,使得 Java NIO 能够高效地处理大量的数据输入输出。

创建ByteBuffer

 @Test
    public void createByteBuffer(){
        ByteBuffer buffer = ByteBuffer.allocate(10);//分配堆内存 10字节 受到GC的影响 读写速度较慢
        ByteBuffer byteBuffer = ByteBuffer.allocateDirect(10);//分配直接内存 读写速度快 但是要分配内存的事件慢
    }

 写数据

  buffer.put(new byte[]{97,98,99});
  buffer.put((byte) 'd');
  //channel.read(buffer);

 

 读数据

buffer.flip();//切换读模式
channel.write()//读数据

  

 byte b = buffer.get();
 System.out.println((char)b);
 b = buffer.get();
 System.out.println((char)b);

buffer.compact();

 buffer.clear();
 System.out.println(buffer.limit());//10

 

buffer.rewind()//  重新读
    mark()与 reset()方法
通过调用 Buffer.mark()方法,可以标记 Buffer 中的一个特定 position。之后可以通
过调用 Buffer.reset()方法恢复到这个 position

   ByteBuffer 与字符串的转换

 /*
      字符串与数组的转换
     */
    @Test
    public void test(){
        //String ------->ByteBuffer
        //使用String.getBytes()方法
        ByteBuffer buffer1 = ByteBuffer.allocateDirect(10);
        buffer1.put("hello".getBytes());
        //使用charset  自动变成读模式也就是position = 0
        ByteBuffer buffer2 = StandardCharsets.UTF_8.encode("hello");

        //使用ByteBuffer.warp()方法 自动变成读模式
        ByteBuffer buffer3 = ByteBuffer.wrap("hello".getBytes());

        //ByteBuffer ---->String
        String str2 = StandardCharsets.UTF_8.decode(buffer2).toString();
        System.out.println(str2);

    }

Scattering Reader

对于已知的数据长度用此方法可以避免字符串的截取

之前的文件内容

 

Gathering  Writer

 减少数据的拷贝与读取的次数

应用 (黏包,半包)

在网络传输过程中。我们可能收到下面的情况。

比如:发送的是hello\n

                        I am zhangsan\n

                        How  are you\n

三个包

但是我们收到的是hello\nI am zhangsan\nHow 

                             are you\n

两个包

    @Test
    public void test11() {
        ByteBuffer source = ByteBuffer.allocate(32);
        source.put("hello\nI am zhangsan\nHow ".getBytes());
        split(source);
        source.put("are you\n".getBytes());
        split(source);
    }

    public void split(ByteBuffer source){
        source.flip();
        for (int i = 0; i < source.limit(); i++) {
            int len = i + 1 - source.position();
            if ((char)source.get(i) == '\n'){
                byte[] data = new byte[32];
                source.get(data,source.position(),len);
                for (int j = 0;j<data.length;j++){
                    System.out.print((char)data[j]);
                }
            }
        }
        source.compact();
    }

猜你喜欢

转载自blog.csdn.net/qq_57533658/article/details/129992542