博客
关于我
强烈建议你试试无所不能的chatGPT,快点击我
BufferedInputStream 源码分析
阅读量:5370 次
发布时间:2019-06-15

本文共 3635 字,大约阅读时间需要 12 分钟。

一、简介

  BufferedInputStream会缓存一部分数据(默认8K),这个函数的作用就是读取更多的数据到缓存,必要的时候会扩大缓存的内容。

在该类中有几个重要的标志位:markpos,pos,count

  【markpos的作用,marklength区域内的数据表示需要保留的数据,也就是在重置(reset 方法)buffer的时候,这部分数据是不会被删除的,强制要求保留。】  

  pos:

    current position in the buffer, this is the index of the next character to be read from the buffer.

    表示下一个即将读入的字符。

  markpos:

    The value of the pos field at the time the last mark method was called.

    markpos 的数值等于上一次调用mark方法时候的pos位置。

1     public synchronized void mark(int readlimit) {2         marklimit = readlimit;3         markpos = pos;4     }

   count:

      可以使用的buffer

 

二、fill()函数

  当pos>count的时候,调用该方法来扩容。它总会将预留空间的位置挪动到buffer的前端。

1 private void fill() throws IOException { 2         byte[] buffer = getBufIfOpen(); 3         if (markpos < 0) 4             pos = 0;            /* no mark: throw away the buffer */ 5         else if (pos >= buffer.length)  /* no room left in buffer */ 6             if (markpos > 0) {  /* can throw away early part of the buffer */ 7                 int sz = pos - markpos; 8                 System.arraycopy(buffer, markpos, buffer, 0, sz); 9                 pos = sz;10                 markpos = 0;11             } else if (buffer.length >= marklimit) {12                 markpos = -1;   /* buffer got too big, invalidate mark */13                 pos = 0;        /* drop buffer contents */14             } else {            /* grow buffer */15                 int nsz = pos * 2;16                 if (nsz > marklimit)17                     nsz = marklimit;18                 byte nbuf[] = new byte[nsz];19                 System.arraycopy(buffer, 0, nbuf, 0, pos);20                 if (!bufUpdater.compareAndSet(this, buffer, nbuf)) {21                     // Can't replace buf if there was an async close.22                     // Note: This would need to be changed if fill()23                     // is ever made accessible to multiple threads.24                     // But for now, the only way CAS can fail is via close.25                     // assert buf == null;26                     throw new IOException("Stream closed");27                 }28                 buffer = nbuf;29             }30         count = pos;31         int n = getInIfOpen().read(buffer, pos, buffer.length - pos);32         if (n > 0)33             count = n + pos;34     }

 

    byte[] buffer = getBufIfOpen(); 获取当前buffer的引用

     if (markpos < 0)

              pos = 0;            /* no mark: throw away the buffer */ 整个buffer没有被标记过,也就是没有预留空间

    else if (pos >= buffer.length)  /* no room left in buffer */   (markpos >0 或=0 )有预留空间,而且没有剩余空间可用。

      if (markpos > 0) {  /* can throw away early part of the buffer */  预留空间的起始位置不在buffer的开始位置

                  int sz = pos - markpos;    挪动预留空间
                  System.arraycopy(buffer, markpos, buffer, 0, sz);
                  pos = sz;
                  markpos = 0;

      } else if (buffer.length >= marklimit) { 如果marklimit的值小于缓存的长度,说明buffer很大,从内存使用的角度考虑,此时不宜再增大缓存的容量,

                         在这种情形下直接丢弃buf中的已有内容;

                  markpos = -1;   /* buffer got too big, invalidate mark */
                  pos = 0;        /* drop buffer contents */

      } else {            /* grow buffer */ 2倍扩展buffer

                  int nsz = pos * 2;
                  if (nsz > marklimit)
                      nsz = marklimit;
                  byte nbuf[] = new byte[nsz];
                  System.arraycopy(buffer, 0, nbuf, 0, pos);
                  if (!bufUpdater.compareAndSet(this, buffer, nbuf)) { 确保多线程情况下的可见性。
                      // Can't replace buf if there was an async close.
                      // Note: This would need to be changed if fill()
                      // is ever made accessible to multiple threads.
                      // But for now, the only way CAS can fail is via close.
                      // assert buf == null;
                      throw new IOException("Stream closed");
                  }
                  buffer = nbuf;
            }

转载于:https://www.cnblogs.com/plxx/p/4794833.html

你可能感兴趣的文章
Python/jquery
查看>>
【BZOJ】【2132】圈地计划
查看>>
Java有没有goto?
查看>>
求不相邻金币相加和的最大值--动态规划1
查看>>
[转][osg]探索未知种族之osg类生物【目录】
查看>>
四十九. Zabbix报警机制 、 Zabbix进阶操作 、 监控案例
查看>>
元类中__new__ 与 __init__的区别--day27
查看>>
占小狼的简书博客
查看>>
struts2__action执行顺序
查看>>
php异常处理
查看>>
[xampp] /usr/bin/env: php: No such file or directory
查看>>
细学PHP 10 贴吧-2
查看>>
黑客攻防入门秘籍
查看>>
Swift迎来了1.0 GM 版(2014.09.09)
查看>>
【iOS开发-68】APP下载案例:利用tableView自带的cell布局+缓存池cell复用时注意button状态的检查...
查看>>
《Genesis-3D开源游戏引擎-FQA常见问题解答》2014年01月10号版本
查看>>
Java 编程下实现随机无重复数字功能
查看>>
Android 编程下的代码混淆
查看>>
animation属性
查看>>
页内的模块和组件抽象规划经验
查看>>