JAVA初级(三十二)I/O流基础(4),字节和字符缓冲流Buffer介绍以及和非缓冲流的效率差距

缓冲流是一个能让字节或字符流高效读取和写入的一种流。

字节流在读取文件时每次读取一个字节都会去操作磁盘
在这里插入图片描述
这样如果数据量大的话,就会很频繁的操作磁盘。效率低下。
但如果使用了缓冲流,JAVA程序就会一次性从磁盘拉取大量数据先放到JAVA内存中。然后在优先从这个内存读取。如果读完了。在重新从磁盘在拉取大量数据。这样就大大的减少了操作磁盘的频率,从内存读取数据的效率要远高于从磁盘读取的效率。
在这里插入图片描述

字节缓冲流

1,字节流使用缓冲流读取数据和不使用缓冲流读取数据对比
(1)字节输入缓冲流BufferInputStream
InputStream下有一个BufferInputStream字节输入缓冲流,它用于实现字节输入流的高效读取。
实例文件目录如下,这是一个6.4M大小左右的文本文件
在这里插入图片描述
字节输入缓冲流创建步骤:
1,创建一个字节输入流比如FileInputStream并令其获取pro文件的File对象
2,创建一个字节输入缓冲流BufferInputStream并令其获取一个字节输入流比如FileInputStream

        File file = new File("F:/java/pro.txt");
        InputStream inputStream = new FileInputStream(file);
        BufferedInputStream bufferedInputStream = new BufferedInputStream(inputStream);

这样就创建完成,接下来就能读取数据了。读取方法和字节输入流一致。今天我们要对比两种读取方法的效率

//字节输入流
  public static void inputStream() throws IOException {
        File file = new File("F:/java/pro.txt");
        InputStream inputStream = new FileInputStream(file);
        long l = System.currentTimeMillis();
        while (inputStream.read()!=-1){ }
        long l1 = System.currentTimeMillis();
        System.out.print(l1-l);
    }

//字节输入缓存流
    public static void bufferInputStream() throws IOException {
        File file = new File("F:/java/pro.txt");
        InputStream inputStream = new FileInputStream(file);
        BufferedInputStream bufferedInputStream = new BufferedInputStream(inputStream);
        long l = System.currentTimeMillis();
        //缓存流高效读取
        while (bufferedInputStream.read()!=-1){ }
        long l1 = System.currentTimeMillis();
        System.out.print(l1-l);
        //关流
    }

分别执行上述两个方法,结果如下:
这是普通字节流
这是普通字节流
这是缓存流
这是缓冲流
可以看到极其明显的效率提升。。

(2)字节输出缓冲流BufferOutputStream
字节输出缓冲流是OutputStream底下的BufferOutputStream,创建过程是一样的。
1,先创建一个File对象指向一个路径,然后在创建一个字节输出流并令其获取这个File对象。
2,接着在创建一个字节缓冲输出流,并令其获取一个字节输出流

        File file = new File("F:/java/pro.txt");
        OutputStream outputStream = new FileOutputStream(file);
        //创建缓冲输出流
        OutputStream bufferedOutputStream = new BufferedOutputStream(outputStream);

接下来同样对比缓存流和非缓存流的效率:
在这里插入图片描述
上图是文件目录,目的是把pro文本里的内容给写到pro1中。也就是复制。我们来看看缓冲流和非缓冲流的速度。

        File file = new File("F:/java/pro.txt");
        File file1 = new File("F:/java/pro1.txt");
        InputStream inputStream = new FileInputStream(file);
        BufferedInputStream bufferedInputStream = new BufferedInputStream(inputStream);
        OutputStream outputStream = new FileOutputStream(file1);
        //缓冲输出流
        OutputStream bufferedOutputStream = new BufferedOutputStream(outputStream);
        int len = 0;
        long l, l1,time = 0L;
        while ((len=bufferedInputStream.read())!=-1){
            l = System.currentTimeMillis();
            //缓冲流
            //bufferedOutputStream.write(len);
            //非缓冲流
            outputStream.write(len);
            l1 = System.currentTimeMillis();
            //这样就能只记录写的时间了
            time+=(l1-l);
        }
        System.out.print(time);
        //关流

分别放开缓冲流和非缓冲流的注释并执行得到以下结果:
非缓冲流
在这里插入图片描述

缓冲流
在这里插入图片描述
可以看到及其明细的效率提升

如果你没有关流或调用flush会发现pro1仍然成功写入了数据,缓冲流不是要调用flush()才会把数据写进去吗?
缓冲流默认的缓冲区大小是8K,也就是说你往这个缓冲区塞的数据超过8K那么它就会自动的刷新缓冲来重新放数据。所以上述使用字节输出缓冲流但没有关流或调用flush()的结果如下
在这里插入图片描述
所以如果发现没调用flush()或关流还是往里面写的数据,原因就是这样。所以实际上还是要调用flush()或关流的。这个别忘了。

字符缓冲流

1,字符输入缓冲流BurrferReader
创建方法:
(1)创建一个字符输入流并令其获取pro文本的File对象
(2)创建一个字符输入缓冲流BurrferReader并令其获取一个字符输入流

        File file = new File("F:/java/pro.txt");
        Reader reader = new FileReader(file);
        //创建一个字符缓冲输入流
        Reader buf = new BufferedReader(reader);
        long l = System.currentTimeMillis();
        //缓冲流
        while (buf.read()!=-1){}
        //非缓冲流
        //while (reader.read()!=-1){ }
        long l1 = System.currentTimeMillis();
        System.out.print(l1-l);

分别放开缓冲流和非缓冲流的注释并执行,结果如下
缓冲流
在这里插入图片描述
非缓冲流
在这里插入图片描述
可以看到有一点效率差距的。

2,字符输出缓冲流BufferWriter
创建方法:
(1)创建一个字符输出流并令其获取pro1文本的File对象
(2)创建一个字符输出缓冲流BufferWriter并令其获取一个字符输出流
同样进行文本文件的复制操作来看看效果
在这里插入图片描述
把文本pro的内容写入到pro1中。大小8.7M左右

        File file = new File("F:/java/pro.txt");
        File file1 = new File("F:/java/pro1.txt");
        Reader reader = new FileReader(file);
        Reader buf = new BufferedReader(reader);
        Writer writer = new FileWriter(file1);
        //字符缓冲输出流
        Writer bufW = new BufferedWriter(writer);
        long l,l1,time=0L;int len;
        while ((len =buf.read())!=-1){
            l = System.currentTimeMillis();
            //缓冲流高效写入
            //bufW.write(len);
            //非缓冲流写入
            writer.write(len);
            l1 = System.currentTimeMillis();
            time+=(l1-l);
        }
      //关流
        System.out.print(time);

分别放开缓冲流和非缓冲流的注释并执行,结果如下
缓冲流:
在这里插入图片描述
非缓冲流:
在这里插入图片描述

可以看到效率的差距.

问题:
1,字符流使用缓冲和非缓冲的速度差距并没有字节流的那么如此大。是否有必要使用缓冲流?
当然是有必要的。虽然没那么多。但还是提升很多的。
2,字符流自带的缓冲和缓冲流的缓冲有什么区别吗?
这个我没具体研究过。但是大致看了下源码。简单来说就是字符流的缓冲实现更复杂。导致速度慢。。。。。有哪个大佬能解释下就更好了

  • 0
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值