【NIO】2. ByteBuffer的基本使用

ByteBuffer的基本使用

  • [1. 项目环境](#1. 项目环境)
  • [2. 示例代码](#2. 示例代码)

使用Java NIO的API来读取文件。

1. 项目环境

maven项目中,引入以下依赖

xml 复制代码
<dependency>
     <groupId>io.netty</groupId>
     <artifactId>netty-all</artifactId>
     <version>4.1.39.Final</version>
</dependency>

准备一个文本文件,其中的文本内容:

text 复制代码
1234567890abc

2. 示例代码

案例1

java 复制代码
public static void main(String[] args) {
        try(FileInputStream fileInputStream = new FileInputStream("src/main/resources/Buffer01_HelloWorld.txt")) {
            // 获取文件channel
            FileChannel channel = fileInputStream.getChannel();

            // 从内存中分配一个buffer,大小为10个字节
            ByteBuffer byteBuffer = ByteBuffer.allocate(10);

            // 从channel中读取数据,并写到buffer中
            channel.read(byteBuffer);

            // flip方法,切换到【读模式】;flip在这里的意思应该是【浏览 / 快速翻阅】
            byteBuffer.flip();

            // 打印buffer中的字节数据
            // 当buffer中还有剩余数据,则不断读取
            while (byteBuffer.hasRemaining()) {
                // 每次只读一个字节
                byte b = byteBuffer.get();
                // 将字节强转成字符,打印
                System.out.println((char) b);
            }

        } catch (IOException e) {
            throw new RuntimeException(e);
        }
    }

以上案例中

  1. 先获取文件数据读取通道:Channel;
  2. 再准备一个大小为10字节的缓存区 Buffer;
  3. 从Channel中读取数据,并写到buffer中;
  4. 再打印Buffer中的数据。

输出结果

text 复制代码
"C:\Program Files\Java\jdk-1.8\bin\java.exe" ...
1
2
3
4
5
6
7
8
9
0
Process finished with exit code 0

从结果中可以看到,文件中的内容并没有全部读取出来,是因为只从文件中读取了一次,并且缓存的大小只有10;

要想读取文件中的全部内容,就要多次读取。

案例2

java 复制代码
public static void main(String[] args) {
        try(FileInputStream fileInputStream = new FileInputStream("src/main/resources/Buffer01_HelloWorld.txt")) {
            // 获取文件channel
            FileChannel channel = fileInputStream.getChannel();

            // 从内存中分配一个buffer,大小为10个字节
            ByteBuffer byteBuffer = ByteBuffer.allocate(10);

            int read;

            // read方法的返回值代表读取到的字节数,当返回值为-1时,代表文件中的所有数据读取完成
            // 使用while一直读取,直到全部读取完
            while ((read = channel.read(byteBuffer)) != -1) {
                System.out.println("读到的字节数:" + read);
                // flip方法,切换到【读模式】;flip在这里的意思应该是【浏览 / 快速翻阅】
                byteBuffer.flip();
                while (byteBuffer.hasRemaining()) {
                    byte b = byteBuffer.get();
                    System.out.println((char) b);
                }
                // buffer中的数据读取完成后,清空buffer的数据
                byteBuffer.clear();
            }

        } catch (IOException e) {
            throw new RuntimeException(e);
        }
    }

以上案例

  1. 在案例一的基础上,多次从channel中读取数据到buffer,并且打印buffer中的数据,直到文件中的内容全部读取完;

  2. buffer中的数据读取完成后,在 再次从channel中读取数据到buffer之前,要清空buffer的数据。

输出结果

jtext 复制代码
"C:\Program Files\Java\jdk-1.8\bin\java.exe" ...
读到的字节数:10
1
2
3
4
5
6
7
8
9
0
读到的字节数:3
a
b
c

Process finished with exit code 0

可以看到一共读取了两次,实际上应该是3次,第一个读取10个字节,第二次读取剩余的3个字节,第三次没有读取到数据,read方法返回-1。

相关推荐
那个松鼠很眼熟w8 天前
【NIO】8. Selector多线程
nio
蚰蜒螟13 天前
从内核启动到 Java NIO:一次 socket accept 的源码串联之旅
java·python·nio
骇客野人15 天前
Java BIO / NIO / AIO 完整详解 + 编程技巧
java·开发语言·nio
那个松鼠很眼熟w20 天前
【NIO】4. ByteBuffer的几个重要方法
nio
那个松鼠很眼熟w20 天前
【NIO】3.1 ByteBuffer的原理
nio
那个松鼠很眼熟w20 天前
【NIO】3.2 ByteBuffer的原理-AI参考
nio
那个松鼠很眼熟w20 天前
【NIO】5. FileChannel的基本用法
nio
今天的砖头有点烫手啊25 天前
Java IO/NIO/AIO 演进:从 BIO 到 Netty 的底层逻辑
java·jvm·nio
名字还没想好☜1 个月前
Java NIO ByteBuffer 实战:flip/clear/compact 三个绕晕人的方法与 position/limit 心智模型
java·开发语言·后端·spring·nio