[重学Java基础][Java IO流] [Part.1] 字符数组输入/输出流
CharArrayReader
概述
CharArrayReader字符数组输入流,继承了所有字符输入流的超类Reader类,是一个具体功能的子类,用于读取字符数组
此类是数据始终储存在内存中的节点流,也可称之为内存流
实际上并没有对外部数据源进行读入操作 直接采用内存中的数据
主要用于适配以字符输入流为参数的接口
源码分析
成员属性
public class CharArrayReader extends Reader {
/** 字符数组缓冲流 */
protected char buf[];
/** 当前字符缓冲流 下一次读取的开始位置*/
protected int pos;
/** 在缓冲流中的被标记的位置. */
protected int markedPos = 0;
/**字符数组缓冲流的长度*/
protected int count;
……
}
可以看到CharArrayReader存在四个成员属性
- 字符数组形式char buf[],实际上就是流的内容体
- 当前字符缓冲流下一次读取的开始位置int pos,每次读取就从pos标记的位置开始
- 在缓冲流中的被标记的位置 int markedPos 用户手动调用以保存当前读取位置
- 流内容长度int count
-
成员方法
成员方法一共有11个,主要的就是读取方法CharArrayReader,标记方法mark,重置方法reset
CharArrayReader构造方法有两个重载,一个直接读入字符数组char buf[]作为输入流,起始位置为0位,流的大小等于字符数组的大小。
public CharArrayReader(char buf[]) {
this.buf = buf;
this.pos = 0;
this.count = buf.length;
}
另一个从指定位置读入入字符数组char buf[]作为输入流,起始位置为指定的offset,读入时从offset位置开始读入数据,读入的大小等于length,流的大小等于读入的length大小,但最大不超过字符数组buf的大小
public CharArrayReader(char buf[], int offset, int length) {
if ((offset < 0) || (offset > buf.length) || (length < 0) ||
((offset + length) < 0)) {
throw new IllegalArgumentException();
}
this.buf = buf;
this.pos = offset;
this.count = Math.min(offset + length, buf.length);
this.markedPos = offset;
}
read方法 读取一个单字符 并移动游标 返回一个整型
public int read() throws IOException {
synchronized (lock) {
ensureOpen();
if (pos >= count)
return -1;
else
return buf[pos++];
}
}
重载和CharArrayReader构造方法类似 加入了初始位置和读入大小
public int read(char b[], int off, int len) throws IOException {
……
}
skip方法 跳过流的一部分内容 入参long n 跳过n大小的字符流内容 下次读入从n+1开始
public long skip(long n) throws IOException {
synchronized (lock) {
ensureOpen();
if (pos + n > count) {
n = count - pos;
}
if (n < 0) {
return 0;
}
pos += n;
return n;
}
}
mark方法 标记当前流读取位置 配合reset方法使用 入参int readAheadLimit 无作用
public void mark(int readAheadLimit) throws IOException {
synchronized (lock) {
ensureOpen();
markedPos = pos;
}
}
reset方法 将流读取位置重置为标记的位置 配合mark方法使用
public void reset() throws IOException {
synchronized (lock) {
ensureOpen();
pos = markedPos;
}
}
代码示例
示例1
char chs[]=new char[] {'a','b','c','d','e','f','g','h','i','j','k','l','m','n'};
//读入字符数组初始化CharArrayReader
CharArrayReader charArrayReader=new CharArrayReader(chs);
int i=0;
//循环读取流内容并打印到控制台 -1结束
while ((i=charArrayReader.read())!=-1)
{
System.out.printf("%s,",(char)i);
}
- 运行结果
a,b,c,d,e,f,g,h,i,j,k,l,m,n
示例2
char chs[]=new char[]{'a','b','c','d','e','f','g','h','i','j','k','l','m','n','o'};
//读入字符数组初始化CharArrayReader
CharArrayReader charArrayReader=new CharArrayReader(chs);
int i=0;
//读入字符流内容并循环输出前5位
for(;i<=4;i++)
{
System.out.printf("%s ",(char)charArrayReader.read());
}
System.out.println();
//保存当前读取位置 已读取5位 所以当前游标在f 下一位正常读入为f
charArrayReader.mark(0);
//跳过5个 所以读入游标移动到k
charArrayReader.skip(5);
for(i=0;i<=4;i++)
{
System.out.printf("%s ",(char)charArrayReader.read());
}
System.out.println();
//重置读入游标到标记的位置
charArrayReader.reset();
for(i=0;i<=4;i++)
{
System.out.printf("%s ",(char)charArrayReader.read());
}
System.out.println();
运行结果
a b c d e k l m n o f g h i j
CharArrayWriter
概述
CharArrayWriter字符数组输出流,继承了所有字符输出流的超类Writer类,是一个具体功能的子类,用于输出字符数组
此类是数据始终储存在内存中的节点流,也可称之为内存流
实际上并没有对外部数据汇进行写入操作 直接写入到内存中
主要用于适配以字符输出流为参数的接口
源码分析
成员属性
public class CharArrayWriter extends Writer {
protected char buf[];
protected int count;
}
字符串数组char buf[] 存储流内容体
流内容大小 int count
成员方法
可以看到主要也就是几个方法
可以初始化字符流数组大小的构造方法
public CharArrayWriter() {
this(32);
}
/**
public CharArrayWriter(int initialSize) {
if (initialSize < 0) {
throw new IllegalArgumentException
("Negative initial size: " + initialSize);
}
buf = new char[initialSize];
}
不同入参的多重载append write方法
public void write(int c) {
synchronized (lock) {
int newcount = count + 1;
if (newcount > buf.length) {
buf = Arrays.copyOf(buf, Math.max(buf.length << 1, newcount));
}
buf[count] = (char)c;
count = newcount;
}
}
public void write(char c[], int off, int len) {
if ((off < 0) || (off > c.length) || (len < 0) ||
((off + len) > c.length) || ((off + len) < 0)) {
throw new IndexOutOfBoundsException();
} else if (len == 0) {
return;
}
synchronized (lock) {
int newcount = count + len;
if (newcount > buf.length) {
buf = Arrays.copyOf(buf, Math.max(buf.length << 1, newcount));
}
System.arraycopy(c, off, buf, count, len);
count = newcount;
}
}
public void write(String str, int off, int len) {
synchronized (lock) {
int newcount = count + len;
if (newcount > buf.length) {
buf = Arrays.copyOf(buf, Math.max(buf.length << 1, newcount));
}
str.getChars(off, off + len, buf, count);
count = newcount;
}
}
reset重置方法
public void reset() {
count = 0;
}
示例代码
示例1
CharArrayWriter charArrayWriter=new CharArrayWriter();
charArrayWriter.write(97);
charArrayWriter.write(98);
charArrayWriter.write(99);
System.out.println(charArrayWriter.toString());
输出结果
abc
示例2
CharArrayWriter charArrayWriter=new CharArrayWriter();
charArrayWriter.write("abcdefg",3,2);
System.out.println(charArrayWriter.toString());
结语
其实这两个类和StringWriter StringReader两个字符串输入\输出流操作类很像
只不过一个流的入参是char型 另一个是String型