Java IO—基本文件字符流FileWriterFileReader
Posted 刘Java
tags:
篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了Java IO—基本文件字符流FileWriterFileReader相关的知识,希望对你有一定的参考价值。
详细介绍了Java IO中的基本文件字符流FileWriter、FileReader的方法以及使用方式。
文章目录
1. IO流概述
IO,即输入和输出。流,即数据的传输,可以看做是一种数据的流动。
按照流动的方向,以内存为基准,分为输入input 和输出output ,即流向内存是输入流,流出内存的输出流,合称IO流。
Java中流的分类:
- 按数据流向:
- 输出流:将内存中的数据流向到外部的介质。
- 输入流:将外部介质的数据流向内存。
- 按数据类型:
- 字节流:处理数据单位是字节,1Byte。
- 字符流:处理数据单位是字符,2Byte。
- 流动方向与操作相结合:
- 字节输入流: InputStream类
- 字节输出流: OutputStream类
- 字符输入流: Reader类
- 字符输出流: Writer类
以上四类都在IO包中,都是顶级抽象类。
2 FileWriter文件字符输出流
public abstract class Writer
extends Object
implements Appendable, Closeable, Flushable
特点:
- 输出到外部。
- 输出的是字符,只能操作文本。
- 作为各个字符输出类的最终抽象基类。所有子类必须实现的方法有 write(char[], int off, int length)、flush() 和 close()。
public class FileWriter
extends OutputStreamWriter
和文件相关的字符输出流,文件的输出。用来写入字符文件的便捷类。用于写入字符流。
2.1 构造器
FileWriter(String fileName)
根据给定的文件名构造一个 FileWriter 对象。filename:String类型的要写入的文件路径。
注意:
- 创建该对象的时候,必须指定一个抽象路径
- 如果指定的文件不存在,将会自动的创建。
- 如果文件存在,会把原来的文件替换。
FileWriter(String fileName, boolean b);
根据给定的文件名以及指示是否附加写入数据的 boolean 值来构造 FileWriter 对象。filename:要写入的文件路径。b:当指定的boolean 值为true,在原有文件的基础上实现续写。
public FileWriter(File file);
根据给定的 File 对象构造一个 FileWriter 对象。
public FileWriter(File file,boolean append);
根据给定的 File 对象构造一个 FileWriter 对象。以及指示是否附加写入数据的 boolean 值确定是将字符写入文件末尾处还是写入文件开始处。
创建输出流到底做了哪些事情?
- 调用系统功能去创建文件。
- 创建输出流对象。
- 把输出流对象指向这个文件。
2.2 API方法
它的方法全部从直接父类OutputStreamWriter和间接父类Writer、Object继承。
public void write(int c);
写入单个字符,要写入的字符包含在给定整数值的16个低位中,16高位被忽略。(底层Int类型的C—>32位二进制数—>保留低位16位—>转换为char类型)
public void write(String str);
写入字符串。
public void write(String str,int off,int len);
写入字符串的某一部分。str:字符串。off:相对初始写入字符的偏移量。len:要写入的字符数。
public void write(char[] cbuf)
写入字符数组。
public abstract void write(char[] cbuf,int off,int len);
写入字符数组某一部分。cbuf:要写入的数组。off:开始写入字符处的偏移量。len:要写入的字符数。
public abstract void flush();
刷新流的缓冲。
public abstract void close();
将流资源关闭。
public String getEncoding();
返回该流使用的字符编码名称。
2.1.1 补充
flush:刷新流的缓冲,流资源没有关闭,资源可以继续使用。
close:将流资源直接关闭。在关闭之前,会自动调用一次flush方法。流资源一旦关闭,不能在次被使用。
为什么一定要close()呢?
- 让流对象变成垃圾,这样就可以被垃圾回收器回收了
- 通知系统去释放跟该文件相关的资源,否则文件句柄等资源会被一直占用,而Java的GC只会回收对象,不会回收相关文件资源。
3 FileReader文件字符输入流
public abstract class Reader
extends Object
implements Readable, Closeable
Reader :字符输入流,用于读取字符流的抽象超类。子类必须实现的方法只有 read(char[], int off, int length) 和 close()。
public class FileReader
extends InputStreamReader
FileReader,和文件相关的字符输入流,可用于读取文件数据。创建对象的时候,如果指定的文件不存在,将抛出异常。
3.1 构造器
public FileReader(String fileName)
throws FileNotFoundException
在给定从中读取数据的文件名的情况下创建一个新 FileReader。
public FileReader(File file)
throws FileNotFoundException
在给定从中读取数据的 File 的情况下创建一个新 FileReader。
public FileWriter(File file, boolean append)
throws IOException
根据给定的 File 对象构造一个 FileWriter 对象。如果第二个参数为 true,则将字节写入文件末尾处,而不是写入文件开始处。即,追加写入而不是覆盖写入。
3.2 API方法
它的方法全部从直接父类InputStreamReader和间接父类Reader、Object继承。
public int read();
一次读取一个字符。返回int类型,如果读取到末尾,返回-1,可以做为循环条件判断结束依据使用。
public int read(char[] cbuf);
将读取的数据存放在字符数组当中,返回的是已读取字符个数,读取的字符数,如果已到达流的末尾,则返回 -1.可以做为循环条件判断结束依据使用。
new String(cbuf,0,read); 转换字符数组。建议:尽量用读取数组的方法来读取数据,可以避免内存与外部介质的频繁交互。
close();
关闭流资源。
3.2.1 补充
为什么read()方法要使用int类型变量来接收返回值呢?
FileReader 的 read 方法返回值是一个int类型的变量来接收的,而read方法在实际中却是以字符形式来进行数据的读取的。返回的是作为整数读取的字符,即返回Unicode码,其范围在 0 到 65535 之间 (0x00-0xffff),也就是说char类型数据是取不到负值的;
int类型数据的取值范围为-2147483648-2147483647,可以取到负值;同时 int 的取值范围又包含 char 的取值范围,这就为使用 int 作为返回值类型提供了可能,因为流需要一个特殊的值来表示流末尾,这个值不应该在 char 的取值范围内,如果使用 char 取值范围内的值作为流末尾标志,那么这个值同样有可能出现在数据流中间作为数据来传输,流在读到这个值的时候会认为已经到达流末尾,后面未读取的数据将被截断。
所以 Java 中选择了使用-1来作为流末尾,这个值不在char的取值范围内,所以不存在数据截断,然而-1又在 int 的取值范围内,同时int的取值范围包含 char的取值范围,所以FileReader下read方法返回的char类型数据直接转为了 int类型。
4 案例
4.1 写入文件
利用Filewriter将字符写入到指定文件中。
public class FilewriterDemo01 {
@Test
public void Test1() throws IOException {
FileWriter file = null;
try {
file = new FileWriter("C:\\\\Users\\\\lx\\\\Desktop\\\\test.txt");
file.write("呵呵");
file.flush();
} catch (IOException e) {
e.printStackTrace();
} finally {
if (file != null) {
file.close();
}
}
}
@Test
public void Test2() throws IOException {
FileWriter file = null;
try {
file = new FileWriter("C:\\\\Users\\\\Administrator\\\\Desktop\\\\a.txt",
true);
file.write("\\r\\n呵呵");
file.flush();
} catch (IOException e) {
e.printStackTrace();
} finally {
if (file != null) {
file.close();
}
}
}
}
4.2 读取文件
利用Filewriter从指定文件中获取字符数据。注意文件应该使用UTF-8编码,否则可能出现乱码。
public class FileReaderDemo01 {
public static void main(String[] args) throws IOException {
FileReader file = null;
try {
file = new FileReader("C:\\\\Users\\\\lx\\\\Desktop\\\\test.txt");
/* int read = 0;
while ((read = file.read()) != -1)
{
System.out.print((char) read);
}*/
char[] ch = new char[1024];
int read = 0;
while ((read = file.read(ch)) != -1) {
System.out.println(new String(ch, 0, read));
}
} catch (IOException e) {
e.printStackTrace();
} finally {
if (file != null) {
file.close();
}
}
}
}
4.3 拷贝文件
注意文件应该使用UTF-8编码,否则可能出现乱码。
利用FileReader和FileWriter实现文件数据的拷贝。
public class Copy {
public static void main(String[] args) throws IOException {
FileWriter filew = null;
FileReader filer = null;
try {
filer = new FileReader("C:\\\\Users\\\\lx\\\\Desktop\\\\test.txt");
filew = new FileWriter("C:\\\\Users\\\\lx\\\\Desktop\\\\target.txt");
/*int read=0;
while ((read=filer.read())!=-1)
{
filew.write((char)read);
}*/
int read = 0;
char[] ch = new char[1024];
while ((read = filer.read(ch)) != -1) {
filew.write(new String(ch, 0, read));
}
filew.flush();
} catch (Exception e) {
throw new RuntimeException("IO异常");
} finally {
if (filer != null) {
filer.close();
}
if (filew != null) {
filew.close();
}
}
}
}
如有需要交流,或者文章有误,请直接留言。另外希望点赞、收藏、关注,我将不间断更新各种Java学习博客!
以上是关于Java IO—基本文件字符流FileWriterFileReader的主要内容,如果未能解决你的问题,请参考以下文章
java字符型文件流 FileReader; FileWriter;