一、主要方法及接口:
public synchronized int read();
private void fill();
public synchronized void mark(int readlimit);
public synchronized void reset();
二、源码解读:
1)public synchronized int read()
重载了父类FilterInputStream的read方法,主要作用还是按照字节从输入流中读取数据,但是第一次调用该方法时,会调用顶级类InputStream中的read(byte b[], int off, int len) 一次读取多个字节,并放到字节数组(defaultsize = 8192)中缓存起来,下次再读取的字节就是从缓存的字节数组中读取到的,直到已经读到最后一个缓存的字节,并且输入流中仍有未读取的数据,则继续读取长度为defaultsize的字节,并继续缓存在字节数组中,见如下代码
public synchronized int read() throws IOException {
if (pos >= count) {
fill();
if (pos >= count)
return -1;
}
return getBufIfOpen()[pos++] & 0xff;
}
private void fill() throws IOException {
byte[] buffer = getBufIfOpen();
if (markpos < 0)
pos = 0; /* no mark: throw away the buffer */
/*.......此处省略其他步骤*/
int n = getInIfOpen().read(buffer, pos, buffer.length - pos);
if (n > 0)
count = n + pos;
read(byte b[], int off, int len)的好处不用多说,自然是为了减少IO的访问次数,提高效率,个人感觉如果仅仅是为了缓存数据,减少IO的访问,大可不必再多此一举,提供BufferedInputStream这样的read方法,更多的秘密在于BufferedInputStream可以通过mark和reset的使用,缓存输入流中访问较为频繁的数据,达到在不访问IO的情况下,重读缓存中的数据。
2)private void fill()
mark标记了待缓存数据的起始位置,fill方法根据mark的位置,通过System.arraycopy缓存部分数据
private void fill() throws IOException {
byte[] buffer = getBufIfOpen();
if (markpos < 0)
pos = 0; /* no mark: throw away the buffer */
else if (pos >= buffer.length) /* no room left in buffer */
if (markpos > 0) { /* can throw away early part of the buffer */
int sz = pos - markpos;
System.arraycopy(buffer, markpos, buffer, 0, sz);
pos = sz;
markpos = 0;
} else if (buffer.length >= marklimit) {
markpos = -1; /* buffer got too big, invalidate mark */
pos = 0; /* drop buffer contents */
} else { /* grow 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;
}
count = pos;
三、适用场景:
1、IO访问频率和次数较低的情况,可以一次读取多个字节
2、读取较大数据(size> 8192),并且待读取的数据需要频繁的被访问,通过mark和set方法,从mark位置开始缓存部分数据,在不访问IO的情况下,直接操作缓存数据
分享到:
相关推荐
主要介绍了Java IO学习之缓冲输入流(BufferedInputStream)的相关资料,需要的朋友可以参考下
2、常用21个IO流:FileWriter、FileReader、...3、JAVA IO流经典代码示例,示例从易到难。代码功能涉及字节、字符、字符串、文本文件、图片、音频、视频。演示错误用法和经典用法。 4、代码的结构可查看README文件。
import java.io.BufferedInputStream; import java.io.BufferedOutputStream; import java.io.File; import java.io.FileNotFoundException; import java.io.FileOutputStream; import java.io.IOException; import ...
JavaIO ##JavaIO基础面试题 1. 什么是IO 它是一种数据的流从源头到目的地。比如文件拷贝,输入流和输出流都包括了。输入流是从文件中读取数据到存储到进程(process)中,输出流是从进程中读取数据然后写入到目标文件...
分析Java常用IO流,包括InputStream、OutputStream、FileInputStream、FileOutputStream、BufferedInputStream、BufferedOutputStream、Reader、Writer、InputStreamReader、OutputStreamWriter、FileReader、...
File类概述、File类功能讲解、JAVA IO流概述、字节流、字符流、缓冲流、InputStream、OutputStream、Reader、Writer、FileInputStream、FileOutputStream、InputStreamReader、OutputStreamWriter、FileReader、...
IO从大的方向上分为字节流和字符流,包括四个抽象类: 1、输入:Reader, InputStream类型的子类(字符,字节) 2、输出:Writer, OutputStream类型的子类(字符,字节) 决定使用哪个类以及它的构造进程的一般...
import java.io.BufferedInputStream; import java.io.BufferedOutputStream; import java.io.File; import java.io.FileInputStream; import java.io.FileOutputStream; import java.util.zip.Zip...
import java.io.BufferedInputStream; import java.io.BufferedReader; import java.io.File; import java.io.FileInputStream; import java.io.InputStreamReader; import java.io.Reader; /** * @author...
InputStream和OutputStream 1.DataInputStream,DataOutputStream 从Stream里读取基本类型的数据 BufferedReader,BufferedWriter...2.BufferedInputStream,BufferedOutputStream 封装了从缓冲区读写指定数量数据的方法
什么是“流”3.Serializable接口4.IO流的分类二、IO基础之File类1. File类介绍2. File类的构造方法3.File类常用方法三、IO流之字节流1.什么是字节流2.字节流的分类3.字节输入流(InputStream)3.1.InputStream类...
is = new BufferedInputStream( new FileInputStream(f) ); long contentLength = f.length(); ByteArrayOutputStream outstream = new ByteArrayOutputStream( contentLength > 0 ? (int) contentLength : 1024)...
import java.io.BufferedInputStream; import java.io.File; import java.io.FileInputStream; import java.io.IOException; import javax.sound.sampled.LineUnavailableException; import javax.sound.sampled....
Java reads and stores large binary data files. The java.io package provides BufferedInputStream and BufferedOutputStream classes to buffer read and write streams
C OutputStream D BufferedInputStream 答案:AC 2. 为了提高读写性能,可以采用什么流?( ) A InputStream B DataInputStream C BufferedReader D BufferedInputStream E OutputStream F BufferedOutputStream ...
Java读存大块二进制资料文件,java.io 包中提供了BufferedInputStream 和BufferedOutputStream 类来缓存的读写流。但是读写大块的数据文件时,使用这两个类的效果并不是很好。本例演示了如何自定义缓存区,并使用不...
import java.io.BufferedInputStream; import javax.swing.*; import javax.swing.border.BevelBorder; import javax.swing.event.*; import javax.swing.filechooser.FileFilter; import javax.swing.text....
实际上Java提供的工具包中,IO相关工具就普遍大量使用了装饰器模式,例如充当装饰功能的IO类如BufferedInputStream等,又被称为高级流,通常将基本流作为高级流构造器的参数传入,将其作为高级流的一个关联对象,...
BufferedInputStream和BufferedOutputStream分别继承于FilterInputStream和FilterOutputStream,代表着缓冲区的输入输出,这里我们就来看一下Java中的BufferedInputStream与BufferedOutputStream使用示例:
|--BufferedInputStream/:输入流缓冲区。 | 为另一个输入流添加一些功能,创建一个缓冲区,支持mark和reset方法。 | mark操作记录输入流中的某个点,reset操作在从包含的输入流获取新字节前,再读取最后一次。 ...