今天我们接着上一篇的知识点继续总结学习,上面讲到了文件流,我们接下来来总结一下过滤流和其他的相关知识点吧!
过滤流
过滤流:缓存作用,用于装配文件磁盘、网络设备、终端等读写开销大的节点流,提高读写性能。
过滤处理
//就是装饰器模式中的抽象装饰角色
public abstract class FilterReader extends Reader { //典型的装饰模式,需要继承 Reader
protected Reader in; //被装饰目标
protected FilterReader(Reader in) {//通过构造器要求定义装饰器对象时必须指定被装饰对象
super(in);
this.in = in;
}
public int read() throws IOException { //调用read方法时,真正执行任务的是被装 饰对象
return in.read();
}
桥接转换流
InputStreamReader用于将一个InputStream 自动转换为 ReaderOutputStreamWriter用于将一个 Writer 自动转换为 OutputStream
构造器
1.InputStreamReader(InputStream)2.InputStreamReader(InputStream in, String charsetName)3.InputStreamReader(InputStream in, Charset cs) ,直接使用 charsetName 编码字符集名称的方式进行设定编码字符集可能会出错,所以可以使用Charset 指定编码字符集名称
// int kk=System.in.read();
// System.out.println((char)kk);//但是由于字节流只读取了一个字节,所以对于多字节 编码的中文就会出现乱码问题
Reader r = new InputStreamReader(System.in); // public final static
InputStream in = null;
int kk = r.read(); //只读取一个字符
System.out.println((char)kk);
String ss = "学习Java";
OutputStream os = new FileOutputStream("out/data.data"); //最终输出使用的是字节流Writer writer = new OutputStreamWriter(os);//引入桥接流自动实现字符流转换为字节流进 行输出 writer.write(ss);
writer.close();
缓冲流
构造器
1.字节流
BufferedInputStream(InputStream)不定义缓存大小,则默认8192 BufferedInputStream(InputStream,int)人为设置缓冲大小,int单位字节 BufferedOutputStream(OutputStream) BufferedOutputStream(OutputStream,int size)自定义缓存区大小
2.字符流
BufferedReader(Reader) 默认缓冲区大小为 8192 字符BufferedReader(Reader,int)int 用于定义缓冲区的大小BufferedWriter(Writer)默认缓冲区大小为8192字符 BufferedWriter(Writer,int)int用于自定义缓冲区的大小,单位为字符B
Reader r=new BufferedReader(new FileReader("data/abc.txt"));
String str=r.readLine(); //系统在编译器不能识别r对象为BufferedReader类型,所以不能直接调用BufferedReader中的特殊
BufferedReader r = new BufferedReader(new FileReader("data/T1.java"));
String ss=r.readLine(); //也可以使用窄化操作
特殊方法
1. 整行读取数据,以 \r 或者 \n 为分隔符 ( 换行符 )如果读取内容为null ,则表示读取到了流末尾readLine方法的返回值会自动剔除末尾的换行符
public class T {
public static void main(String[] args) throws IOException {
BufferedReader r = new BufferedReader(new FileReader("data/T1.java"));
String ss = r.readLine();
while (ss != null) {
if (ss.trim().length() > 0)
System.out.println(ss); //使用println表示输出结束后自动换行,通过这种方式可以给readLine剔除的换行符进行补偿
ss = r.readLine();
}
r.close();
}
}
2.BufferedWriter中提供了一个方法newLine可以写入一个换行符
public class T {
public static void main(String[] args) throws IOException {
BufferedReader r = new BufferedReader(new FileReader("data/T1.java"));
String ss = r.readLine();
while (ss != null) {
if (ss.trim().length() > 0)
System.out.println(ss+"\n"); //在字符串末尾手动添加\n也可以补偿 换行符
ss = r.readLine();
}
r.close();
}
}
一般使用缓存流的目标是在于以透明的方式引入缓冲区,以提高代码的执行效率,所以不会使用什么特殊的方法,还是使用Reader/Writer、InputStream/OutputStream之类的父类中提供的方法
特殊的是BufferedReader方法readLine
过滤流使用必须有对应的节点流,因为过滤流是用于装饰节点流的,不是有具体的操作目标
执行close方法会自动关闭被装饰的对象,所以不需要再关闭FileReader、FileWriter
执行 flush 方法会自动刷新数据到被装饰的流上,但是并没有执行关闭流。针对输出流关闭时会自动先 flush 然后再关闭
数据流
构造器
DataInputStream(InputStream)DataOutputStream(OutputStream)
打印流
//print(Object):void/println(Object):void
PrintWriter pw = new PrintWriter(new FileWriter("out/pw.txt"));
for(int i=0;i<10;i++) {
pw.print("数值:"+i);
pw.print(i);
pw.println(i%2==0);
}
pw.close();
特殊构造器
public PrintWriter (Writer out)PrintWriter(Writer out,boolean autoFlush) boolean 表示是否支持自动刷新PrintWriter(OutputStream out) 直接使用 OutputStream 时不需要通过桥接处理PrintWriter(OutputStream out, boolean autoFlush)PrintStream(OutputStream out)PrintStream(OutputStream out, boolean autoFlush)PrintStream(String fileName) 参数为文件名称,表示数据直接输出到指定文件中PrintStream(File file)
对象流
//账户类定义
public class Account {
private Long id;//账户编号
private String username;//账户名称
private String password;//账户口令
private Double balance;//余额
}
//添加账户数据
public class Regist {
public static void main(String[] args) throws IOException {
BufferedReader br = new BufferedReader(new InputStreamReader(System.in));
System.out.println("账户编号:");
String ss=br.readLine();
Long id=Long.valueOf(ss);
System.out.println("账户名称:");
String username=br.readLine(); System.out.println("账户口令:");
String password=br.readLine(); System.out.println("存款数量:");
ss=br.readLine(); double balance=Double.parseDouble(ss);
DataOutputStream dos=new DataOutputStream(new FileOutputStream("out/account.data",true));
dos.writeLong(id);
dos.writeUTF(username);
dos.writeUTF(password);
dos.writeDouble(balance);
dos.close();
}
}
//显示账户信息
public class Show {
public static void main(String[] args) throws Exception {
DataInputStream dis = new DataInputStream(new FileInputStream("out/account.data"));
while (true) {
try {
Long id = dis.readLong();
String username=dis.readUTF();
String password=dis.readUTF();
double balance=dis.readDouble();
System.out.println(id+"\t"+username+"\t"+password+"\t"+balance);
} catch (EOFException e) {
break;
}
}
dis.close();
}
}
Java 提供了 ObjectInputStream 和 ObjectOutputStream 可以直接读写 Object 对象,实际上还提供了针对8种简单类型和 String 类型的读写操作方法ObjectInputStream 提供了方法 readObject():ObjectObjectOutputStream 提供了方法 writeObject(Object):void