(82)IO概述、字符流写入、异常处理、续写、两种读取方式、读写练习
来源:互联网 发布:石油化工数据 编辑:程序博客网 时间:2024/06/05 15:01
一、IO流概述
IO流用来处理设备之间的数据传输
Java对数据的操作是通过流的方式
Java用于操作流的对象都是在IO包中
流按照操作数据分为两种:字节流、字符流
流按流向分为:输入流、输出流
二、IO流常用基类
①字节流的抽象基类:InputStream ,OutputStream
②字符流的抽象基类:Reader、Writer
注意:由这四类派生出来的子类名称都是以其父类作为子类名的后缀
如:InputStream的子类FileInputStream
Reader的子类FileReader
三、IO字符流
既然IO流是用于操作数据的,所以数据的最常见体现形式是:文件
那么先以操作文件为主来演示
需求:在硬盘上,创建一个文件并写入一些文字数据
找到一个专门用于操作文件的Writer子类对象:FileWriter,后缀名是父类名,前缀名为该流对象的功能。
FileWriter类的构造函数没有不含参数的原因:要想操作文件,必须现有文件。即该流对象一一初始化,就必须保证文件存在
java.lang.Object
——–java.io.Writer
——–java.io.OutputStreamWriter
———java.io.FileWriter
以下演示的是创建流、输入流(以及输入到文件中)、关闭流进行演示,这些步骤记住
package Demo;import java.io.*;public class Demo { public static void main(String[] args)throws IOException { /*创建一个FileWriter对象,该对象一被初始换,就必须含有被操作的文件 *而且该文件会创建到指定的目录下,如果该目录下有同名文件,将被覆盖 *其实该步就是在明确数据要存放的目的地 */ FileWriter fw=new FileWriter("demo.txt"); //调用write方法,将字符串写入流(流在内存的缓冲区中)中 //调用flush方法,就能将流中的数据,存入到文件(目的地)中 fw.write("adhuwifcb"); fw.flush(); /*注意每次写入,都必须flush *关闭流资源,但是关之前会默认刷新一次内存的缓冲区中的数据。 *将数据刷到目的地。 *和flush的区别:flush刷新后,流可以继续使用,close刷新后,会将流关闭 */ fw.write("hahah"); fw.close(); fw.write("ooooooo");//流关闭,不能再将数据写入流中,更不能写入文件中 }}
IO处理方式标准解决方式
import java.io.*;public class IOexception { public static void main(String[] args) { /* * 在io操作中,都会抛出异常,但是不能每个操作都trycatch * 原因是:比如文件创建不成功,若解决了这个问题,相当于将该问题隐藏 * 之后的操作都无效,因为文件都没建立起来,写还有关等其他操作都没意义,不用再执行了 */ FileWriter fw=null;//必须在外建立引用,否则在finally中fw无法识别 try { fw=new FileWriter("demo.txt"); fw.write("bjdi"); } catch(IOException e) { System.out.println(e.toString()); } /* * 注意不论操作成功,还是操作异常,被catch捕获,最终都要把流关闭 * 但是关资源,也会发生异常,所以要单独try下 */ finally { try { if(fw!=null)/* * 写if 的原因是若文件流创建不成功,则fw就还是null,没有指向谁,就无从谈起关闭了, * 若不写该句,会抛出NullPointerException异常 */ { fw.close();} } catch (IOException e) { System.out.println(e.toString()); } } }}
因为上面的代码带有解释,比较乱。所以下面再写个纯代码形式
public static void main(String[] args) { FileWriter fw=null; try { fw=new FileWriter("k:\\demo.txt"); fw.write("bjdi"); } catch(IOException e) { System.out.println(e.toString()); } finally { try { if(fw!=null) fw.close(); } catch (IOException e) { System.out.println(e.toString()); } }} }
文件的续写:就是在原来文件内容的基础上,继续写内容:
public FileWriter(String fileName, boolean append) throws IOException
fileName:一个字符串,表示与系统有关的文件名
append:一个boolean值,如果为true,则将数据写入文件末尾处,而不是写入文件开始处
public class Demo3 {public static void main(String[] args) { FileWriter fw=null; try { fw=new FileWriter("demo.txt",true);//在构造函数处指定文件,确定是否续写 fw.write("kkkkkkkkk");//在文本的末尾写 fw.write("nihao\r\nheihei");//记事本中\r\n为换行。写入字符串 char[] ch= {'h','e','l','l','o'};//也可以写入字符数组 fw.write(ch); } catch(IOException e) { System.out.println(e.toString()); } finally { try { if(fw!=null) fw.close(); } catch(IOException e) { System.out.println(e.toString()); } } }}
java.lang.Object
——–java.io.Reader
——–java.io.InputStreamWriter
———java.io.FileReader
文本读取的第一种方式
/*创建一个文件读取流对象并且指定名称的文件相关联 * 要保证该文件是已经存在的,如果不存在,会发生FileNotFoundException(io异常的子类)异常 */ FileReader fr=new FileReader("demo.txt"); System.out.println("----------读取的第一种方式----------------"); /* * 调用读取流对象的read方法 * read():一次读一个字符,而且会自动往下读 */ int ch=0;//到达流的末尾返回-1,所以有了循环的条件 while((ch=fr.read())!=-1) { System.out.println("ch="+(char)ch); }
说明:reader()方法每次读一个,读完一个字符后,指针自动到文本的下一个字符,直到字符的末尾 返回-1。所以可以用用结尾字符-1作为循环条件,输出文本所有数据
文本读取的第二种方式
System.out.println("----------读取的第二种方式----------------"); /* * 通过字符数组进行读取 */ //定义一个字符数组,用于存储读到的字符,该read(char[])返回的是字符个数 char[] buf=new char[3]; int num=fr.read(buf); System.out.println("num="+num+new String(buf)); int num1=fr.read(buf); System.out.println("num1="+num1+new String(buf)); int num2=fr.read(buf); System.out.println("num2="+num2+new String(buf));
public int read(char[] cbuf):返回读取的字符数,如果到达流的末尾,则返回-1
说明:左图为流,右图为存放字符的数组,有三个空间。
①开始时,流指针指向a,将a存入ch[0]中,读出后,流指针和数组指针均向后移。
此时,流指针指向b,将b存入ch[1]中,读出后,流指针和数组指针均向后移。
此时,流指针指向c,将c存入ch[2]中,读出后,流指针和数组指针均向后移,数组指向-1,已经存不下数据了,所以不会再在从流中读取数据,并且read(char[])=3,返回存的个数。
②再次调用read(char[ ])由①知流指针指向d,数组的指针在末尾自动返回到ch[0](因为它向一个数组里面装数据),所以将def存入数组,之后,流指针指向g,数组指针指向末尾,read(char[])=3。
③再次调用read(char[ ])由②知,流指针指向g,数组指针执行ch[0],所以将g存入ch[0]中,流指针指向-1,没数据不能再读了,所以read(char[])=1(只读了一个数据),在打印的时候,打印的是数组字符串,所以打印gef
因为只读到了一个,所以取出这一个就可以了。
int num1=fr.read(buf);
System.out.println(“num1=”+num1+new String(buf,0,num1));//这样就只输出个g
【public String(char[] value, int offset, int count)】
offset:初始偏移量
count:长度
④再次调用read(char[ ])由③知,流指针指向-1,没有数据可读,read(char[])=-1(没读数据,返回-1),打印的还是字符数组,所以仍然是gef.
第二种读取的循环形式:
char[] buf=new char[3]; int num=0; while((num=fr.read(buf))!=-1) { System.out.println("num="+num+" "+new String(buf,0,num)); }输出:num=3 abc num=3 def num=1 g
在实际开发中,字符数组char[] buf=new char[1024];短的可以一次就打印完,长的也可以减少循环数。
两种读取方式中第二种比较好,因为它可以有效减少循环次数,方式一循环次数太多。
练习:将c盘的一个文件复制到d盘中
复制的原理:
1,在D盘创建一个文件,用于存储c盘文件的数据
2,定义读取流和c盘文件相关联
3,通过不断的读写完成数据存储
4,关闭资源
import java.util.*;import java.io.*;public class Demo4 { public static void main(String[] args) { FileWriter fw=null; FileReader fr=null; try { fw=new FileWriter("DemoCopy.java"); fr=new FileReader("C:\\Demo.java"); int num=0; char[] buf=new char[1024]; while ((num=fr.read(buf))!=-1) { fw.write( buf,0,num);//可以写数组 fw.flush(); } } catch(IOException e) { throw new RuntimeException("读写失败"); } finally { try { if(fw!=null) fw.close(); }catch(IOException e) { throw new RuntimeException("原文件关闭失败"); } try { if(fr!=null) fr.close(); }catch(IOException e) { throw new RuntimeException("复制后关闭失败"); } } }}
图示表示这个复制过程
- (82)IO概述、字符流写入、异常处理、续写、两种读取方式、读写练习
- IO流一:概述、IO异常处理、文件续写、文件读取、文件拷贝及练习
- IO 字符流 FileWriter IO异常的处理 字符数据续写 FileReader 复制原理:
- 06-IO流(字符流-FileReader-读取方式一 1 2 07-IO流(字符流-两种读取方式 12
- 字符流的两种读取方式
- io处理流的读取与写入
- IO流--IO异常的处理方式
- IO流(IO异常处理方式)
- IO异常处理的两种格式
- 02-IO流(输入输出!字节流&字符流) 03-IO流(字符流-FileWriter). 04-IO流(字符流-FileWriter-细节(换行和续写)) 05-IO流(异常处理)12
- IO流中以字符流读取和写入。
- 黑马程序员 IO 字符流中 的读取 和 写入
- 【unity】c# 读写xml_写入xml的两种方式
- 黑马程序员——018——IO流③(读取/写入转换流(码表)、流操作规律、PrintStream、异常处理)
- IO流中字符流FileWriter的最基本建立方式和异常处理
- 文件读写——以字符方式读取与写入文件
- IO流的异常处理方式
- IO流_throws的方式处理异常
- 2.Iris数据集:感知器模型的简单实战(分类)
- 搭建 Seafile 专属网盘
- WCF基本实现(Server和Client)
- SIFT特征提取分析
- 上手上路之 js 数据类型 number和parseInt..的代码笔记
- (82)IO概述、字符流写入、异常处理、续写、两种读取方式、读写练习
- scrapy爬虫返回403
- 【转】阿里巴巴 Java 开发手册 (第一部分:编程规约)
- 初学者的Selenium自动化测试指南,基于Python(六)——如何设置元素等待
- PostGIS中的常用函数
- Oracle的Nvl函数用法
- 【study】僵尸进程
- JVM内存三大核心区域不详解及示例
- Android判断网络是否可用并且开启网络