先看下继承关系和方法:
也是一种装饰流,需要传入一个InputStream类型的对象!
先说一下,这个可以回退的流:
比如:
... D C B A ->
| 从 A 开始读取,把A取出来之后,就不想取出来了,再放回去!哈哈,不可思议,unbelievable哈。
其实,PushbackInputStream是把A
又放回了缓冲区里了。
再读的时候,从缓冲区里读,读到的又是A
!
代码:演示一哈:
public class BufferedReaderTestClient {
public static void main(String[] args) {
try (PushbackInputStream inputStream = new PushbackInputStream(new FileInputStream("Test"))) {
int data = inputStream.read();
inputStream.unread(data);
System.out.println("data = " + data);
data = inputStream.read();
System.out.println("data = " + data);
} catch (Exception exception) {
}
}
}
这里,我们用的是第一种构造函数:
public PushbackInputStream(InputStream in) {
this(in, 1);
}
缓冲区是1
.
public PushbackInputStream(InputStream in, int size) {
super(in);
if (size <= 0) {
throw new IllegalArgumentException("size <= 0");
}
this.buf = new byte[size];
this.pos = size;
}
可以看出,用一个参数的构造函数,int size
默认大小就是1
.
因此,再代码里的int data = inputStream.read()
是读取了一个字节,inputStream.unread(data)
又把读取的字节放回了缓冲区里,data = inputStream.read()
再次去读时,是从缓冲区里读取的,所以2次的data是一样的。
如果,想回退两个字节呢?
inputStream.unread(data);
操作执行2次,因为缓冲区默认是1,操作执行2次缓冲区会溢出,就会抛出异常!
如果,不想抛出异常,就要用第二种构造器:
public class BufferedReaderTestClient {
public static void main(String[] args) {
try (PushbackInputStream inputStream = new PushbackInputStream(new FileInputStream("Test"), 4)) {
int data = inputStream.read();
inputStream.unread(data);
inputStream.unread(data);
System.out.println("data = " + data);
data = inputStream.read();
System.out.println("data = " + data);
data = inputStream.read();
System.out.println("data = " + data);
} catch (Exception exception) {
}
}
}
这个时候,缓冲区设置成了4个字节,就可以回退多个了,但是不能超过,构造参数指定的参数的大小(4个)!
这种流,了解一下即可!(个人认为,用到了再深入研究)