Netty - 文件编程

suaxi
2026-06-22 / 0 评论 / 1 阅读 / 正在检测是否收录...

3. 文件编程

3.1 FileChannel

FileChannel 只能工作在阻塞模式下

(1)获取

通过 FileInputStream(读)、FileOutputStream(写)、RandomAccessFile(根据指定的模式决定读或写) 的 getChannel() 方法获取


(2)读取

// 返回值表示读取的字节,-1 表示读取到了文件的末尾
int readBytes = channel.read(bf);


(3)写入

ByteBuffer bf = ByteBuffer.allcate(16);
bf.put(...);
bf.flip();

// 后续还有值则继续写入,channel.write() 方法不一定能一次写完全部内容
while (bf.hasRemaining()) {
    channel.write(bf);
}


(4)关闭

channel 使用完后必须关闭,可以使用 try-with-resources 语法糖或手动关闭 channel.close()


(5)获取当前位置

// 获取位置
long position = channel.position();

// 设置指定下标索引位置
channel.position(123);

如果设置为文件末尾:

  • 这时进行读取,返回值为 -1
  • 执行写入时,会进行追加,如果 position 超过了文件末尾,新内容和原末尾之间会产生空洞(00)


(6)大小

channel.size();


(7)强制写入

写入的数据在操作系统的管理下并不是立刻写入磁盘,而是先到缓存中,可以通过 channel.force(true) 方法将文件内容和元数据进行立即写入


3.2 两个 Channel 传输数据

package com.sw.netty._01;

import java.io.FileOutputStream;
import java.net.URL;
import java.nio.channels.FileChannel;
import java.nio.file.Paths;

public class FileChannelTransferToTest {
    public static void main(String[] args) {
        URL resource = ScatteringReadsTest.class.getClassLoader().getResource("ByteBufferTest.txt");
        if (resource == null) {
            throw new IllegalArgumentException("resource not found: ScatteringReadsTest.txt");
        }

        // try (FileChannel from = FileChannel.open(Paths.get(resource.toURI()));
        //      FileChannel to = new FileOutputStream("FileChannelTransferTo.txt").getChannel()) {
        //     // transferTo 一次最多传输 2G 的数据
        //     from.transferTo(0, from.size(), to);
        // } catch (Exception e) {
        //     e.printStackTrace();
        // }

        try (FileChannel from = FileChannel.open(Paths.get(resource.toURI()));
             FileChannel to = new FileOutputStream("FileChannelTransferTo.txt").getChannel()) {

            // 传输大于 2G 的文件
            long size = from.size();
            for (long left = size; left > 0; ) {
                left -= from.transferTo((size - left), left, to);
            }
        } catch (Exception e) {
            e.printStackTrace();
        }
    }
}
0

评论 (0)

取消