字符流 FileReader 和 FileWriter
FileReader 和 FileWriter 是使用字符直接对文件的读与写操作
FileReader
构造方法 | 说明 |
---|---|
FileReader(File file) | 在给定从中读取数据的 File 的情况下创建一个新 FileReader |
FileReader(FileDescriptor fd) | 在给定从中读取数据的 FileDescriptor 的情况下创建一个新 FileReader |
FileReader(String fileName) | 在给定从中读取数据的文件名的情况下创建一个新 FileReader |
FileWriter
构造方法 | 说明 |
---|---|
FileWriter(File file) | 根据给定的 File 对象构造一个 FileWriter 对象 |
FileWriter(File file, boolean append) | 根据给定的 File 对象构造一个 FileWriter 对象 |
FileWriter(FileDescriptor fd) | 构造与某个文件描述符相关联的 FileWriter 对象 |
FileWriter(String fileName) | 根据给定的文件名构造一个 FileWriter 对象 |
FileWriter(String fileName, boolean append) | 据给定的文件名以及指示是否附加写入数据的 boolean 值来构造 FileWriter 对象 |
示例
使用FileReader和FileWriter类完成文本文件复制,步骤:
- 创建读(FileReader)对象
- 创建写(FileWriter)对象
- 循环读取的数据,写入到目标文件中
- 关闭写(FileWriter)对象
- 关闭读(FileReader)对象
关于读写对象的关闭顺序不可变
一次读一个字符
/**
* 文本文件复制,一次读一个字符
*
* @param fr
* @param fw
* @throws IOException
*/
public static void copy1(FileReader fr, FileWriter fw) throws IOException {
int ch;
while ((ch = fr.read()) != -1) {// 读数据
fw.write(ch);// 写数据
}
fw.flush();
}
一次读一个字符数组
/**
* 文本文件复制,一次读一个字符数组
*
* @param fr
* @param fw
* @throws IOException
*/
public static void copy2(FileReader fr, FileWriter fw) throws IOException {
char chs[] = new char[1024];
int len = 0;
while ((len = fr.read(chs)) != -1) {// 读数据
fw.write(chs, 0, len);// 写数据
}
fw.flush();
}
测试
public static void main(String[] args) throws IOException {
// 创建输入流对象
// 文件不存在会抛出java.io.FileNotFoundException
FileReader fr = new FileReader("d:\\Test\\copyfrom.txt");
// 创建输出流对象
FileWriter fw = new FileWriter("d:\\Test\\copyto.txt");
// 创建输出流做的工作: 1、调用系统资源创建了一个文件 2、创建输出流对象 3、把输出流对象指向文件
copy1(fr, fw);
copy2(fr, fw);
fr.close();
fw.close();
}
字符缓冲流BufferedReader和BufferedWriter
缓冲流可以读取到一个字节/字符,先不输出,等凑足了缓冲的最大容量后一次性写出去,从而提高了工作效率
优点:减少对硬盘的读取次数,降低对硬盘的损耗
BufferedReader
字符缓冲流具备文本特有的表现形式,行操作
public class BufferedReader extends Reader
- 从字符输入流中读取文本,缓冲各个字符,从而实现字符、数组和行的高效读取。
- 可以指定缓冲区的大小,或者可使用默认的大小。大多数情况下,默认值就足够大了。
- 通常,Reader 所作的每个读取请求都会导致对底层字符或字节流进行相应的读取请求。因此,建议用 BufferedReader 包装所有其 read() 操作可能开销很高的 Reader(如 FileReader 和 InputStreamReader)
BufferedReader 有一个新方法:readLine 。可以一次读取一行数据。
BufferedWriter
BufferedReader in = new BufferedReader(new FileReader("foo.in"));
- 将缓冲指定文件的输入。如果没有缓冲,则每次调用 read() 或 readLine() 都会导致从文件中读取字节,并将其转换为字符后返回,而这是极其低效的。
public class BufferedWriter extends Writer
将文本写入字符输出流,缓冲各个字符,从而提供单个字符、数组和字符串的高效写入。
可以指定缓冲区的大小,或者接受默认的大小。在大多数情况下,默认值就足够大了。
该类提供了 newLine() 方法,它使用平台自己的行分隔符概念,此概念由系统属性 line.separator 定义。并非所有平台都使用新行符 ('\n') 来终止各行。因此调用此方法来终止每个输出行要优于直接写入新行符。
-
通常 Writer 将其输出立即发送到底层字符或字节流。除非要求提示输出,否则建议用 BufferedWriter 包装所有其 write() 操作可能开销很高的 Writer(如 FileWriters 和 OutputStreamWriters)。例如,
PrintWriter out = new PrintWriter(new BufferedWriter(new FileWriter("foo.out")));
缓冲 PrintWriter 对文件的输出。如果没有缓冲,则每次调用 print() 方法会导致将字符转换为字节,然后立即写入到文件,而这是极其低效的。
示例
使用BufferedReader和BufferedWriter完成文件复制
使用 char 做数据读取
/**
* 和字符流一样,使用 char 做数据读取
* @param source
* @param target
* @throws IOException
*/
public static void byteCopy(String source, String target) throws IOException {
// 创建输入流对象
BufferedReader br = new BufferedReader(new FileReader(source));// 文件不存在会抛出java.io.FileNotFoundException
// 创建输出流对象
BufferedWriter bw = new BufferedWriter(new FileWriter(target));
// 文本文件复制
char[] chs = new char[1024];
int len = 0;
while ((len = br.read(chs)) != -1) {
bw.write(chs, 0, len);
}
// 释放资源
br.close();
bw.close();
}
BufferedReader对象使用 readLine 方法读取数据
/**
* BufferedReader对象使用 readLine 方法读取数据
* @param source
* @param target
* @throws IOException
*/
public static void stringCopy(String source, String target) throws IOException {
// 创建输入流对象
// 文件不存在会抛出java.io.FileNotFoundException
BufferedReader br = new BufferedReader(new FileReader(source));
// 创建输出流对象
BufferedWriter bw = new BufferedWriter(new FileWriter(target));
String str = br.readLine();
while (null != str ) {
//一定是先写入数据,然后再读取下一行。
//注意默认没有换行,所以需要自己添加换行符
bw.write(str +"\n");
str = br.readLine();
}
// 释放资源
br.close();
bw.close();
}
测试
public static void main(String[] args) throws IOException {
byteCopy("d:/source.txt" , "d:/target.txt");
stringCopy("d:/source.txt" , "d:/target.txt");
}