Java NIO深入理解通道之间数据传输

前言

Github:https://github.com/yihonglei/java-all

Project:java-nio

在Java NIO中,如果两个通道中有一个是FileChannel,那你可以直接将数据从一个channel(通道)传输到另外一个channel。

通道之间数据传输方法:transferFrom(),transferTo()。

一 transferFrom

FileChannel的transferFrom()方法可以将数据从源通道传输到FileChannel中。

package com.lanhuigu.nio.transfer;

import java.io.FileInputStream;
import java.io.FileOutputStream;
import java.io.IOException;
import java.nio.channels.FileChannel;

/**
 * FileChannel中transferFrom源码:
 * public abstract long transferFrom(ReadableByteChannel src, long position, long count) throws IOException;
 * FileChannel的transferFrom()方法可以将数据从源通道传输到FileChannel中。
 *
 * @author yihonglei
 */
public class TransferFromTest {
    /**
     * 文件复制: 将fromFile.txt文件内容复制到toFile.txt中
     */
    public static void main(String[] args) {
        try (
                // 指定文件创建文件输入流
                FileInputStream fis = new FileInputStream("C:\\mycode\\fromFile.txt");
                // 指定文件创建文件输出流
                FileOutputStream fos = new FileOutputStream("C:\\mycode\\toFile.txt");
                // 获取通道
                FileChannel fromChannel = fis.getChannel();
                FileChannel toChannel = fos.getChannel();
        ) {
            // 定义position的位置为初始位置0
            long position = 0;

            // 获取文件总的字节数
            long count = fromChannel.size();

            // 从fromChannel通道缓冲区position位置开始读取count字节数写入到目标通道toChannel中
            toChannel.transferFrom(fromChannel, position, count);
        } catch (IOException e) {
            e.printStackTrace();
        }
    }
}

方法的输入参数position表示从position处开始向目标文件写入数据,count表示最多传输的字节数。

如果源通道的剩余空间小于count个字节,则所传输的字节数要小于请求的字节数。

此外要注意,在SoketChannel的实现中,SocketChannel只会传输此刻准备好的数据(可能不足count字节)。

因此,SocketChannel可能不会将请求的所有数据(count个字节)全部传输到FileChannel中。

2、transferTo

transferTo()方法将数据从FileChannel传输到其他的Channel中。

package com.lanhuigu.nio.transfer;

import java.io.FileInputStream;
import java.io.FileOutputStream;
import java.io.IOException;
import java.nio.channels.FileChannel;

/**
 * FileChannel的transferTo源码:
 * public abstract long transferTo(long position, long count, WritableByteChannel target) throws IOException;
 * transferTo()方法将数据从FileChannel传输到其他的Channel中。
 *
 * @author yihonglei
 */
public class TransferToTest {
    /**
     * 文件复制: 将fromFile.txt文件内容复制到toFile.txt中
     */
    public static void main(String[] args) {
        try (
                // 指定文件创建文件输入流
                FileInputStream fromFile = new FileInputStream("C:\\mycode\\fromFile.txt");
                // 指定文件创建文件输出流
                FileOutputStream toFile = new FileOutputStream("C:\\mycode\\toFile.txt");
                // 获取通道
                FileChannel fromChannel = fromFile.getChannel();
                FileChannel toChannel = toFile.getChannel()) {

            // 定义position的位置为初始位置0
            long position = 0;

            // 获取文件总的字节数
            long count = fromChannel.size();

            // 从fromChannel通道缓冲区position位置开始读取count字节数写入到目标通道toChannel中
            fromChannel.transferTo(position, count, toChannel);
        } catch (IOException e) {
            e.printStackTrace();
        }
    }
}

这两个实例除了调用方法的FileChannel对象不一样外,其他的都一样。

上面所说的关于SocketChannel的问题在transferTo()方法中同样存在。

SocketChannel会一直传输数据直到目标buffer被填满。

你可能感兴趣的:(#,---NIO)