Java学习笔记 (二十七) 使用NIO写文件

使用Channel 写数据

代码如下:

    public static  void main(String []args){
       try(FileOutputStream fos=new FileOutputStream("fos.txt"))
       {
          //获取文件通道
           FileChannel fc=fos.getChannel();
           //创建 字节缓冲区
           ByteBuffer byteBuffer=ByteBuffer.allocate(1024);
           byteBuffer.put("I LOVE YOU".getBytes());
           //翻转
           byteBuffer.flip();
           //写出缓冲区的数据
           fc.write(byteBuffer);
       }catch (Exception e){
           e.printStackTrace();
       }
    }

创建NIO Path 对象

Path对象是对 文件 或者目录的路径的引用. Path 类似于 FIle ,可以引用文件系统的绝对路径或者相对路径。
Path 创建对象可以使用 工厂类 java.nio.files.Paths ,它有一个静态的get()方法。
如下:

 //创建 相对路径文件的引用
Path path1=Paths.get("love.txt");
//创建绝对路径文件的引用
Path path2=Paths.get("E:\\my project\\blog\\Java-study-io\\love.txt");
//创建绝对路径文件夹的 引用
Path path3=Paths.get("E:\\my project\\blog\\Java-study-io");
//创建绝对路径文件的引用 会拼接成 E:\my project\blog\Java-study-io\love.txt
Path path4=Paths.get("E:\\my project", "\\blog","\\Java-study-io","\\love.txt");

使用java.nio.file.Files中的 write() 方法来写入文件

代码如下:

public static void main(String[] args) throws Exception{
        Path path= Paths.get("love.txt");
        String info="I love three things in this worlds,the sun,the moon,and you.sun for morning, moon for night,and you for ever";
        Files.write(path,info.getBytes() );
    }

很简单的方法,但是这个方法最好不要操作大文件,因为write()方法是通过字节流来实现的。
write()方法源码如下:

    public static Path write(Path path, byte[] bytes, OpenOption... options)
        throws IOException
    {
        // ensure bytes is not null before opening file
        Objects.requireNonNull(bytes);

        try (OutputStream out = Files.newOutputStream(path, options)) {
            int len = bytes.length;
            int rem = len;
            while (rem > 0) {
                int n = Math.min(rem, BUFFER_SIZE);
                out.write(bytes, (len-rem), n);
                rem -= n;
            }
        }
        return path;
    }

从上面的源码可以看出,write()是通过OutputStream来实现写入文件的.

使用Files.newBufferedWriter()来写入文件

代码如下:

public static void main(String[] args) {
        Path path = Paths.get("love.txt");
        try (BufferedWriter bw = Files.newBufferedWriter(path
                , Charset.forName("utf-8"))) {
            bw.write("浮世万千,吾爱有三,日,月和你,日为朝,月为暮,卿为朝朝暮暮.");
        }catch (Exception e){
            e.printStackTrace();
        }
    }

很容易就可以看出来,上面代码是通过字符流来写入文件的,通过Files.newBufferedWriter(path
, Charset.forName(“utf-8”))创建了字符流。
查看 newBufferedWriter()源码:

    public static BufferedWriter newBufferedWriter(Path path, Charset cs,
                                                   OpenOption... options)
        throws IOException
    {
        CharsetEncoder encoder = cs.newEncoder();
        Writer writer = new OutputStreamWriter(newOutputStream(path, options), encoder);
        return new BufferedWriter(writer);
    }

使用Files.copy()来完成文件的复制

代码如下:

public static void main(String[] args) {
        Path oldFile = Paths.get("love.txt");
        Path newFile = Paths.get("newLove.txt");

        try (OutputStream os = new FileOutputStream(newFile.toFile())) {
            Files.copy(oldFile, os);
        } catch (Exception e) {
            e.printStackTrace();
        }
    }

很简洁的方法,copy的源码如下:

    public static long copy(Path source, OutputStream out) throws IOException {
        // ensure not null before opening file
        Objects.requireNonNull(out);

        try (InputStream in = newInputStream(source)) {
            return copy(in, out);
        }
    }

可以看到获取了老的文件的输入流,继续查看copy源码:

 private static long copy(InputStream source, OutputStream sink)
        throws IOException
    {
        long nread = 0L;
        byte[] buf = new byte[BUFFER_SIZE];
        int n;
        while ((n = source.read(buf)) > 0) {
            sink.write(buf, 0, n);
            nread += n;
        }
        return nread;
    }

很明白了,通过老文件的输入流读取字节数组,通过新文件的输出流将字节数组写到新文件。

参考资料

1.Java Nio Write File Example

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值