1.IO的基本概念
FileOutputStream
import java.io.FileNotFoundException;
import java.io.FileOutputStream;
import java.io.IOException;
/**
* @author 作者 张迁:
* @version 创建时间:2019年8月2日 上午9:19:09
* 类说明
* IO流划分:
*1.按方向分:输入流、输出流
*2.按单位分:字节流、字符流(读取数据的单位)
*读文本文件:字符流
*文本文件,图片、视频(二进制文件):字节流
*3.按功能分:节点流、处理流
*你可以认为处理流功能更强大
*
*字节流两个抽象父类:OutputStream,InputStream
*子类:FileOutputStream,FileInputStream---节点流
*1)对异常直接抛出,不处理的方式
2)采用标准处理异常的方式
3)实现对文件内容的追加 默认是覆盖的
4)如果文件不存在,会出现什么情况? 不会报错,会创建
* 如果有一级目录不存在,会直接创建目录和文件吗 不会
*
*文件读写编码不一致会出现乱码
*/
public class FileOutputStreamTest {
public static void main(String[] args) /*throws IOException*/ {
//---------1.往文件中写内容-------
/*FileOutputStream fos = new FileOutputStream("a.txt");
fos.write("12132".getBytes());
fos.close();*/
//--------2.捕获异常-------------
FileOutputStream fos = null;
try {
fos = new FileOutputStream("a.txt",true);//追加
fos.write("Hello".getBytes());
} catch (FileNotFoundException e) {
// TODO Auto-generated catch block
e.printStackTrace();
} catch (IOException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}finally {
if(fos!=null){
try {
fos.close();
} catch (IOException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
}
}
}
}
FileInputStream
/**
* @author 作者 张迁:
* @version 创建时间:2019年8月2日 上午10:04:49 类说明 5)采用逐个字节的读取方式 如果文件不存在,会出现什么情况
* 5)采用逐个字节的读取方式
如果文件不存在,会出现什么情况 会报错
*/
public class FileInputStreamTest {
public static void main(String[] args) {
FileInputStream fis = null;
try {
fis = new FileInputStream("a.txt");
// 1.采用逐个字节的读取方式
/*int data = fis.read();//一个中文为两个字节,utf-8为三个字节
while (data != -1) {
System.out.print((char)data);
data = fis.read();
}*/
//2.采用字节数组方式读取
byte[] b = new byte[1024];
/*int len = fis.read(b);
while(len!=-1){
//byte[]--->String;参数1:字节数组,参数2:偏移为0,参数3:长度
System.out.println(new String(b,0,len));
len = fis.read(b);
}*/
int len;
while((len=fis.read(b))!=-1){
System.out.println(new String(b,0,len));
}
} catch (FileNotFoundException e) {
// TODO Auto-generated catch block
e.printStackTrace();
} catch (IOException e) {
// TODO Auto-generated catch block
e.printStackTrace();
} finally {
CloseUtils.closeAll(fis);
/*try {
fis.close();
} catch (IOException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}*/
}
}
}
自己实现的关闭IO流的类
public class CloseUtils {
//可变参数:... 实参有多少个,就有多少对应可变形参
//本质:数组
public static void closeAll(Closeable... cs) {
for(Closeable c:cs){
if(c!=null){
try {
c.close();
} catch (IOException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
}
}
}
}
copy文件
public class CopyTest {
public static void main(String[] args) throws IOException {
FileInputStream fis = new FileInputStream("a.txt");
FileOutputStream fos = new FileOutputStream("b.txt");
byte[] b = new byte[1024];
int len;
while((len=fis.read(b))!=-1){
fos.write(b, 0, len);
}
CloseUtils.closeAll(fis,fos); //统一资源关闭
}
}
2.字节流(输入、输出)
字节流是最早出现的流,因为计算机保存文件的最小单位就是字节
成对出现的
API为我们提供了两个字节流的基类
public abstract class InputStream
extends Object
implements Closeable
此抽象类是表示字节输入流的所有类的超类。
public abstract class OutputStream
extends Object
implements Closeable, Flushable
此抽象类是表示输出字节流的所有类的超类。
BufferedOutputStream
设计模式:装饰者模式
public class BufferedInputStream
extends FilterInputStream
BufferedInputStream 为另一个输入流添加一些功能,在创建 BufferedInputStream 时,会创建一个内部缓冲区数组。
public class FilterOutputStream
extends OutputStream
此类是过滤输出流的所有类的超类。这些流位于已存在的输出流(基础 输出流)之上,它们将已存在的输出流作为其基本数据接收器,但可能直接传输数据或提供一些额外的功能。
public class BufferedOutputStream
extends FilterOutputStream
该类实现缓冲的输出流。通过设置这种输出流,应用程序就可以将各个字节写入底层输出流中,而不必针对每次字节写入调用底层系统。
import java.io.BufferedOutputStream;
import java.io.FileNotFoundException;
import java.io.FileOutputStream;
import java.io.IOException;
/**
* @author 作者 张迁:
* @version 创建时间:2019年8月2日 上午11:23:40
* 类说明
*
* 带缓冲的字节流:
* 作用:减少了与磁盘交互的次数--提高性能
*
* 默认缓冲区大小----恒定值:8*1024字节
*
* 处理流:包装了节点流,得到了更为强大的流
*
* 设计模式:装饰者模式
*
*/
public class BufferedOpStreamTest {
public static void main(String[] args) throws IOException {
BufferedOutputStream bos = new BufferedOutputStream(new FileOutputStream("a.txt"),5);
bos.write("到周末了..".getBytes());
//bos.flush();
//bos.close(); //刷新+关闭
}
}
BufferedInputStream
public class BuffInStreamTest {
public static void main(String[] args) throws IOException {
BufferedInputStream bos = new BufferedInputStream(new FileInputStream("a.txt"));
byte[] b = new byte[1000];
int len;
while((len=bos.read(b))!=-1){
System.out.println(new String(b,0,len));
}
}
}
IO流-字符流
public abstract class Reader
extends Object
implements Readable, Closeable
用于读取字符流的抽象类。子类必须实现的方法只有 read(char[], int, int) 和 close()。但是,多数子类将重写此处定义的一些方法,以提供更高的效率和/或其他功能。
public abstract class Writer
extends Object
implements Appendable, Closeable, Flushable
写入字符流的抽象类。子类必须实现的方法仅有 write(char[], int, int)、flush() 和 close()。但是,多数子类将重写此处定义的一些方法,以提供更高的效率和/或其他功能。
public class InputStreamReader
extends Reader
转换流
InputStreamReader 是字节流通向字符流的桥梁:它使用指定的 charset 读取字节并将其解码为字符。它使用的字符集可以由名称指定或显式给定,或者可以接受平台默认的字符集。
public class OutputStreamWriter
extends Writer
OutputStreamWriter 是字符流通向字节流的桥梁:可使用指定的 charset 将要写入流中的字符编码成字节。它使用的字符集可以由名称指定或显式给定,否则将接受平台默认的字符集。
OutputStreamWriter
public class OutputStreamWriterTest {
public static void main(String[] args) throws IOException {
OutputStreamWriter osw = new OutputStreamWriter(new FileOutputStream("a.txt"));
osw.write("字符串输出流。。。");
osw.close();
}
}
InputStreamReader
public class InputStreamReaderTest {
public static void main(String[] args) throws IOException {
InputStreamReader isr = new InputStreamReader(new FileInputStream("a.txt"));
char[] cs = new char[1024];
int len;
while((len=isr.read(cs))!=-1){
System.out.println(new String(cs,0,len));
}
isr.close();
}
}
`
2.为了简化上述代码的编写,API给上述的两种转换流都提供了相关的子类
public class FileWriter
extends OutputStreamWriter
用来写入字符文件的便捷类。此类的构造方法假定默认字符编码和默认字节缓冲区大小都是可接受的。要自己指定这些值,可以先在 FileOutputStream 上构造一个 OutputStreamWriter。
public class FileReader
extends InputStreamReader
用来读取字符文件的便捷类。此类的构造方法假定默认字符编码和默认字节缓冲区大小都是适当的。要自己指定这些值,可以先在 FileInputStream 上构造一个InputStreamReader。
FileWriter
/**
* @author 作者 张迁:
* @version 创建时间:2019年8月2日 下午2:29:04
* 类说明
* 富二代流:
* FileWriter:用于简化代码
*
* 结论:如果能用富二代,用富二代流更简洁;如果用不了,则使用父类---字符转换流
*/
public class FileWriterTest {
public static void main(String[] args) throws IOException {
FileWriter fw = new FileWriter("a.txt");
fw.write("富二代流");
fw.close();
}
}
FileReader
public class FileReaderTest {
public static void main(String[] args) throws IOException {
FileReader fr = new FileReader("a.txt");
char[] cs = new char[1024];
int len = fr.read(cs);
System.out.println(new String(new String(cs,0,len) ));
fr.close();
}
}
3.自带缓冲区的流
public class BufferedReader
extends Reader
从字符输入流中读取文本,缓冲各个字符,从而实现字符、数组和行的高效读取。
可以指定缓冲区的大小,或者可使用默认的大小。大多数情况下,默认值就足够大了。
public class BufferedWriter
extends Writer
将文本写入字符输出流,缓冲各个字符,从而提供单个字符、数组和字符串的高效写入。
可以指定缓冲区的大小,或者接受默认的大小。在大多数情况下,默认值就足够大了。
BufferedWriter
/**
* @author 作者 张迁:
* @version 创建时间:2019年8月2日 下午2:39:39
* 类说明
* 字符缓冲流:BufferedWriter/BufferedReader
* 提高字符流的读写效率---减少与磁盘交互次数
* 字符流提供了特有的功能:换行读写:readLine,newLine
*/
public class BuffWrTest {
public static void main(String[] args) throws IOException {
BufferedWriter bw = new BufferedWriter(new FileWriter("a.txt"));
for(int i=0;i<5;i++){
bw.write("好好学习,天天向上");
bw.newLine(); //换行
}
bw.close();
}
}
BufferedReader
import java.io.BufferedReader;
import java.io.FileReader;
import java.io.FileWriter;
import java.io.IOException;
/**
* @author 作者 张迁:
* @version 创建时间:2019年8月2日 下午2:45:58
* 类说明
*/
public class BufferedRTest {
public static void main(String[] args) throws IOException {
BufferedReader br = new BufferedReader(new FileReader("a.txt"));
String msg;
while((msg=br.readLine())!=null){
System.out.println(msg);
}
}
}