欢迎您访问程序员文章站本站旨在为大家提供分享程序员计算机编程知识!
您现在的位置是: 首页

Java基础知识点总结--从细节再看Java(七)--字符输入输出(I/O)流、缓冲流

程序员文章站 2022-04-03 19:35:23
...

字符输入输出(I/O)流 用来解决设备间数据传输的问题。包括文件copy,读写文件,上传文件以及下载文件等。

Java基础知识点总结--从细节再看Java(七)--字符输入输出(I/O)流、缓冲流

对于到底是输入流还是输出流,我们是站在Java程序的角度来看待的,对于程序来说从文件中读取数据即使像程序中输入数据,因此就是输入流,相反则是输出流。

一、输出流

输出流 即往文件中写数据,我们需要用到 java.io.FileWriter 这个类。

  • 构造方法

FileWriter ( String fileName ) : 传递一个文件名称,执行写入时,会覆盖文件原来的内容。

FileWriter ( String fieName, boolean append ) : 当append为true时,执行写入会追加到原文件中(追加时不换行)。

  • 写数据流程

1. 创建输出流对象;

2. 调用该对象的写数据方法;

3. 刷新缓冲区;

4. 释放资源;

public class FileWriteDemo {

	public static void main(String[] args) throws IOException {

		// 创建对象
		FileWriter fw = new FileWriter("f:\\test.txt");

		// 调用write方法写数据
		fw.write("Hello Java IO.");

		// 刷新缓冲区
		fw.flush();

		// 释放资源,通知系统释放和该文件相关的资源
		fw.close();
	}

}

创建对象时,系统为我们做了三件事情:1.调用系统资源创建一个文件 2.创建输出流对象 3.把对象指向文件。同时需要注意,如果我们在写构造函数参数的时候,没有加上盘符,则文件创建的路径为当前项目的相对路径。

执行write方法后接着打开文件会发现write中的内容并没有写入到文件中,这是因为:硬盘存储数据的基本单位是字节,而我们却是一次性写字符串,这样的话字符串是写不进去,其数据全部存储在缓冲区中。因此,我们需要调用flush()方法来刷新缓冲区。

close()方法在释放资源前,会先检查缓冲区中的数据,如果缓冲区中还存在数据,则会先执行一次flush操作。

  • 常用的写数据方法,对write()方法的重载

void write (String str) : 写字符串,上示代码中已经展示过了。

void write (String str , int index, int len) :写字符串中的部分数据,从index开始,长度为len。

void write (int ch) :写一个字符数据,既可以是char 类型又可以是char 类型对应的int 值。

void write (char[ ] chs) :写一个字符数组。

void write (char[ ] chs, int index, int len) :写字符数组的部分数据,从index开始,长度len。

public class FileWriteDemo {

	public static void main(String[] args) throws IOException {

		FileWriter fw = new FileWriter("f:\\test.txt");

            //写入:llo Jav
		fw.write("Hello Java IO.",2,7);

            //换行
        fw.write("\r\n");

            //写入:a
		fw.write('a');
            //写入:a
		fw.write(97);

            //换行
        fw.write("\n");

		char[] chs = {'a','b','c','d','e'};
            //写入: abcdef
		fw.write(chs);

            //换行
        fw.write("\r");

            //写入: cde
		fw.write(chs,2,3);

		fw.close();
	}
}

二、输入流

输入流 即从文件中读数据,我们需要用到 java.io.FileReader 这个类。

  • 构造方法

FileReader ( String fileName ) : 传文件名称。

  • 写数据流程

1. 创建输入流对象;

2. 调用该对象的读数据方法;

3. 释放资源;

import java.io.FileReader;
import java.io.IOException;

public class FileReaderDemo {

	public static void main(String[] args) throws IOException {

		//创建对象
		FileReader fr = new FileReader("f:\\test.txt");

		int ch ;
		//调用读取数据的方法
		while ((ch = fr.read()) != -1){
			System.out.print((char) ch);
		}

		//释放资源
		fr.close();
	}

}

read()方法一次只能读取一个字符的值,并且返回这个字符的整型值。每执行一次read(),就会指向下一个字符,当返回值为-1时,代表没有值了,因此可以用来当作判断条件。你说文件中有-1怎么办?--完全没关系,因为-1在文件中那是两字符。。。

 

  • 常用方法

int  read ( char [ ] chs) : 一次读取一个字符数组的数据, 返回实际读取的字符的个数,并将chs 的值改为读取的数据。chs 数组的大小一般为1024或1024的整数倍。重复执行read方法,当文件中还有数据时会指向下一组数据,当文件中的字符全部读取后,继续执行read()会返回-1,可以用来当作判断条件。

read()返回本次实际读取的字符的个数,换行符( \n, \r )也算一个。因此,如果最后一次读取的字符个数不是chs 定义的长度,即len<chs.length,新chs 数组在len 之前是读取的新数据,len之后的数据会保留上一次的结果,当直接输出显示数组时会重复显示len之后的内容。所以我们用new String(chs,0,len) 来输出,保证没有多余的内容。

public class FileReaderDemo {

	public static void main(String[] args) throws IOException {

		FileReader fr = new FileReader("f:\\test.txt");
		
		char[] chs = new char[1024];
		int len ;
		while((len = fr.read(chs)) != -1){
			System.out.print(new String(chs,0,len));
		}
		
		fr.close();
	}
}

 

三、字符缓冲流

BufferedWriter : 文本写入字符输出流,缓冲各个字符,实现高效写入。
BufferedReader : 从字符输入流中读取文本,缓冲各个字符,高效读出。

字符缓冲流与IO流进行文本的读写步骤唯一不同的是创建对象,不再是创建FileWriter和FileReader对象,而是:

创建输出缓冲流对象
        BufferedWriter bw = new BufferedWriter(new FileWriter("f:\\test.txt"));

 创建输入缓冲流对象
        BufferedReader br = new BufferedReader(new FileReader("f:\\test.txt"));

bw,br 与fw,fr有相同的功能,唯一的区别是使用字符缓冲流更加高效。

 

四、缓冲流的特殊功能

BufferedWriter 

void newLine() : 写一个由系统决定的换行符(win:\r\n ; Linux:\n ; mac:\r)。

BufferedReader

String readLine() : 一次读取不包括换行符的一行,返回一个字符串。读取不到数据会返回null,可作为结束的条件。

public class BufferedStreamDemo {

	public static void main(String[] args) throws IOException {

		// 创建输出缓冲流对象
		BufferedWriter bw = new BufferedWriter(new FileWriter("f:\\test.txt"));

		for (int i = 0; i < 10; i++) {
			bw.write("hello");
			//写一个换行符
			bw.newLine();
			bw.flush();
		}

		// 释放资源
		bw.close();

		// 创建输入缓冲流对象
		BufferedReader br = new BufferedReader(new FileReader("f:\\test.txt"));

		String line;
		while ((line = br.readLine()) != null) {
			//readLine()不读取换行符,因此可以用println()来输出
			System.out.println(line);
		}

		// 释放资源
		br.close();
	}
}