....

输入流和输出流相对于内存设备而言. 将外设中的数据读取到内存中:输入 将内存的数写入到外设中:输出。 字符流的由来: 其实就是:字节流读取文字字节数据后,不直接操作而是先查指定的编码表。获取对应的文字。 在对这个文字进行操作。简单说:字节流+编码表 --------------------------------------- 字节流的两个顶层父类: 1,InputStream 2,OutputStream. 字符流的两个顶层父类: 1,Reader 2,Writer 这些体系的子类都以父类名作为后缀。 而且子类名的前缀就是该对象的功能。 就从熟悉的文字开始字符流, //需求:将一些文字存储到硬盘一个文件中。 记住;如果要操作文字数据,建议优先考虑字符流。 而且要将数据从内存写到硬盘上,要使用字符流中的输出流。Writer 硬盘的数据基本体现是文件。 希望找到一个可以操作文件的Writer. 找到了FileWriter //需求:读取一个文本文件。将读取到的字符打印到控制台. 同上,找到了FileReader 作业:将c盘的一个文本文件复制到d盘。 分析: 复制原理: 读取c盘文件中的数据, 将这些数据写入到d盘当中。 连读带写。 ========================== 字符流缓冲区: BufferedWriter :newLine(); BufferedReader: : readLine(); 使用缓冲区复制一个文本文件。 装饰设计模式: 对一组对象的功能进行增强时,就可以使用该模式进行问题的解决。 装饰和继承都能实现一样的特点:进行功能的扩展增强。 有什么区别呢? 首先有一个继承体系。 Writer |--TextWriter:用于操作文本 |--MediaWriter:用于操作媒体。 想要对操作的动作进行效率的提高。 按照面向对象,可以通过继承对具体的进行功能的扩展。 效率提高需要加入缓冲技术。 Writer |--TextWriter:用于操作文本 |--BufferTextWriter:加入了缓冲技术的操作文本的对象。 |--MediaWriter:用于操作媒体。 |--BufferMediaWriter: 到这里就哦了。但是这样做好像并不理想。 如果这个体系进行功能扩展,有多了流对象。 那么这个流要提高效率,是不是也要产生子类呢?是。这时就会发现只为提高功能,进行的继承, 导致继承体系越来越臃肿。不够灵活。 重新思考这个问题? 既然加入的都是同一种技术--缓冲。 前一种是让缓冲和具体的对象相结合。 可不可以将缓冲进行单独的封装,哪个对象需要缓冲就将哪个对象和缓冲关联。 class Buffer{ Buffer(TextWriter w) {} Buffer(MediaWirter w) { } } class BufferWriter extends Writer{ BufferWriter(Writer w) { } } Writer |--TextWriter:用于操作文本 |--MediaWriter:用于操作媒体。 |--BufferWriter:用于提高效率。 装饰比继承灵活。 特点:装饰类和被装饰类都必须所属同一个接口或者父类。 -------------------------------------- 字节流: InputStream OutputStream 字节流: FileInputStream FileOutputStream BufferedInputStream BufferedOutputStream 字符流: Writer Reader FileReader FileWriter BufferedReader BufferedWriter ================================================================ 转换流: InputStreamReader :字节到字符的桥梁。解码。 OutputStreamWriter:字符到字节的桥梁。编码。 流的操作规律: 之所以要弄清楚这个规律,是因为流对象太多,开发时不知道用哪个对象合适。 想要知道开发时用到哪些对象。只要通过四个明确即可。 1,明确源和目的(汇) 源:InputStream Reader 目的:OutputStream Writer 2,明确数据是否是纯文本数据。 源:是纯文本:Reader 否:InputStream 目的:是纯文本 Writer 否:OutputStream 到这里,就可以明确需求中具体要使用哪个体系。 3,明确具体的设备。 源设备: 硬盘:File 键盘:System.in 内存:数组 网络:Socket流 目的设备: 硬盘:File 控制台:System.out 内存:数组 网络:Socket流 4,是否需要其他额外功能。 1,是否需要高效(缓冲区); 是,就加上buffer. 2,转换。 需求1:复制一个文本文件。 1,明确源和目的。 源:InputStream Reader 目的:OutputStream Writer 2,是否是纯文本? 是! 源:Reader 目的:Writer 3,明确具体设备。 源: 硬盘:File 目的: 硬盘:File FileReader fr = new FileReader("a.txt"); FileWriter fw = new FileWriter("b.txt"); 4,需要额外功能吗? 需要,需要高效。 BufferedReader bufr = new BufferedReader(new FileReader("a.txt")); BufferedWriter bufw = new BufferedWriter(new FileWriter("b.txt")); ================================================ 需求2:读取键盘录入信息,并写入到一个文件中。 1,明确源和目的。 源:InputStream Reader 目的:OutputStream Writer 2,是否是纯文本呢? 是, 源:Reader 目的:Writer 3,明确设备 源: 键盘。System.in 目的: 硬盘。File InputStream in = System.in; FileWriter fw = new FileWriter("b.txt"); 这样做可以完成,但是麻烦。将读取的字节数据转成字符串。再由字符流操作。 4,需要额外功能吗? 需要。转换。 将字节流转成字符流。因为名确的源是Reader,这样操作文本数据做便捷。 所以要将已有的字节流转成字符流。使用字节-->字符 。InputStreamReader InputStreamReader isr = new InputStreamReader(System.in); FileWriter fw = new FileWriter("b.txt"); 还需要功能吗? 需要:想高效。 BufferedReader bufr = new BufferedReader(new InputStreamReader(System.in)); BufferedWriter bufw = new BufferedWriter(new FileWriter("b.txt")); =================================================== 需求3:将一个文本文件数据显示在控制台上。 1,明确源和目的。 源:InputStream Reader 目的:OutputStream Writer 2,是否是纯文本呢? 是, 源:Reader 目的:Writer 3,明确具体设备 源: 硬盘:File 目的: 控制台:System.out FileReader fr = new FileReader("a.txt"); OutputStream out = System.out;//PrintStream 4,需要额外功能吗? 需要,转换。 FileReader fr= new FileReader("a.txt"); OutputStreamWriter osw = new OutputStreamWriter(System.out); 需要,高效。 BufferedReader bufr = new BufferedReader(new FileReader("a.txt")); BufferedWriter bufw = new BufferedWriter(new OutputStreamWriter(System.out)); ================================================================ 需求4:读取键盘录入数据,显示在控制台上。 1,明确源和目的。 源:InputStream Reader 目的:OutputStream Writer 2,是否是纯文本呢? 是, 源:Reader 目的:Writer 3,明确设备。 源: 键盘:System.in 目的: 控制台:System.out InputStream in = System.in; OutputStream out = System.out; 4,明确额外功能? 需要转换,因为都是字节流,但是操作的却是文本数据。 所以使用字符流操作起来更为便捷。 InputStreamReader isr = new InputStreamReader(System.in); OutputStreamWriter osw = new OutputStreamWriter(System.out); 为了将其高效。 BufferedReader bufr = new BufferedReader(new InputStreamReader(System.in)); BufferedWriter bufw = new BufferedWriter(new OutputStreamWriter(System.out)); ============================================================ 5,将一个中文字符串数据按照指定的编码表写入到一个文本文件中. 1,目的。OutputStream,Writer 2,是纯文本,Writer。 3,设备:硬盘File FileWriter fw = new FileWriter("a.txt"); fw.write("你好"); 注意:既然需求中已经明确了指定编码表的动作。 那就不可以使用FileWriter,因为FileWriter内部是使用默认的本地码表。 只能使用其父类。OutputStreamWriter. OutputStreamWriter接收一个字节输出流对象,既然是操作文件,那么该对象应该是FileOutputStream OutputStreamWriter osw = new OutputStreamWriter(new FileOutputStream("a.txt"),charsetName); 需要高效吗? BufferedWriter bufw = new BufferedWriter(new OutputStreamWriter(new FileOutputStream("a.txt"),charsetName)); 什么时候使用转换流呢? 1,源或者目的对应的设备是字节流,但是操作的却是文本数据,可以使用转换作为桥梁。 提高对文本操作的便捷。 2,一旦操作文本涉及到具体的指定编码表时,必须使用转换流 。
原文地址:https://www.cnblogs.com/xiaowei88/p/5536893.html