Java - Contents2 (character stream)

character stream

Why is there a character stream
? Because byte streams are not particularly convenient for manipulating Chinese, Java provides character streams.

  • Character stream = byte stream + encoding table

When copying a text file with a character stream, the text file will also have Chinese, but there is no problem. The reason is that the underlying operation will automatically perform byte splicing into Chinese. How to identify it as Chinese?

  • When Chinese characters are stored, no matter which encoding is selected for storage, the first byte is a negative number

For example:
insert image description here

import java.io.FileInputStream;
import java.io.IOException;
import java.util.Arrays;

/*
需求:字节流读文本文件数据

	一个汉字的存储:
		如果是GBK编码,占用2个字节
		如果是UTF-8编码,占用3个字节

*/

public class FileInputStreamDemo3 {
    
    
	public static void main(String[] args) throws IOException{
    
    
//		FileInputStream fis=new FileInputStream("..\\hello java\\a.txt");
//		
//		int by;
//		while((by=fis.read())!=-1) {
    
    
//			System.out.print((char)by);
//		}
//		
//		fis.close();
		
//		String s="abc";//[97, 98, 99]
		
		String s="中国";//[-42, -48, -71, -6] 默认GBK编码
//		byte[] bys = s.getBytes();
		
//		byte[] bys = s.getBytes("UTF-8");//[-28, -72, -83, -27, -101, -67]
		byte[] bys = s.getBytes("GBK");//[-42, -48, -71, -6]
		System.out.println(Arrays.toString(bys));
		
		
	}
}

code list

Basic knowledge:

  • The information stored in the computer is represented by binary numbers; the English, Chinese characters and other characters we see on the screen are the results of binary number conversion
  • According to certain rules, characters are stored in the computer, which is called encoding . Conversely, parsing and displaying the binary numbers stored in the computer according to certain rules is called decoding . Here I would like to emphasize: it is stored according to the A code, and must be parsed according to the A code, so that the correct text symbols can be displayed. Otherwise it will cause garbled characters.
    Character encoding: It is a set of correspondence rules between natural language characters and binary numbers (A, 65)

character set:

  • It is a collection of all characters supported by the system, including national characters, punctuation marks, graphic symbols, numbers, etc.
  • In order for a computer to accurately store and recognize a character set symbol, character encoding is required. A character set must have at least one character encoding.
    Common character sets include ASCII character set, GBXXX character set, Unicode character set, etc.

ASCII character set:

  • ASCII (American Standard Code for Information Interchange, American Standard Code for Information Interchange): It is a computer coding system based on the Latin alphabet, used to display modern English, mainly including control characters (enter key, backspace, line feed, etc.) and Displayable characters (English uppercase and lowercase characters, Arabic numerals and Western symbols)
  • The basic ASCII character set, using 7 to represent a character, a total of 128 characters. The ASCII extended character set uses 8 bits to represent a character, with a total of 256 characters, which is convenient for supporting common European characters. It is a collection of all characters supported by the system, including national characters, punctuation marks, graphic symbols, numbers, etc.

GBXXX character set:

  • GB2312: Simplified Chinese code table. The meaning of a character less than 127 is the same as before, but when two characters greater than 127 are connected together, it represents a Chinese character, so that more than 7,000 simplified Chinese characters can be combined, in addition to mathematical symbols, Roman Greek letters, Japanese characters The pseudonyms and so on have been compiled into it, and even the numbers, punctuation, and letters that already existed in ASCII have been rewritten and compiled into a two-byte long code. The following ones are called "half-width" characters
  • GBK : The most commonly used Chinese code table. It is an extended specification based on the GB2312 standard, using a double-byte encoding scheme, and contains a total of 21,003 Chinese characters, fully compatible with the GB2312 standard, and supports traditional Chinese characters, Japanese and Korean Chinese characters, etc.
  • GB18030: The latest Chinese code table. A total of 70,244 Chinese characters are included, which adopt multi-byte encoding, and each character can consist of 1, 2 or 4 bytes. Supports the languages ​​of ethnic minorities in China, as well as traditional Chinese characters, Japanese and Korean Chinese characters, etc.

Unicode character set:

  • Designed to express any character in any language, it is a standard in the industry, also known as Unicode and Standard Universal Code. It uses up to 4 bytes of numbers to represent each letter, symbol, or text. There are three encoding schemes, UTF-8, UTF-16 and UTF32. The most commonly used UTF-8 encoding
  • UTF-8 encoding: It can be used to represent any character in the Unicode standard. It is the preferred encoding for email, web pages, and other applications that store or transmit text. The Internet Engineering Task Force (IETF) requires that all Internet protocols must support UTF-8 encoding. It uses one to four bytes to encode each character Encoding
    rules:
    128 US-ASCII characters, only one byte is needed to encode
    Latin and other texts, two bytes are needed to encode
    most common words (including Chinese), use three byte encoding
    Other rarely used Unicode auxiliary characters, using four-byte encoding

Summary: Which kind of rule encoding is used, it is necessary to use the corresponding rule to decode, otherwise there will be garbled characters

Encoding and decoding problems in strings

coding:

  • byte[] getBytes(): Use the platform's default character set to encode the String as a series of bytes and store the result in a new byte array
  • byte[] getBytes(String charsetName): Encode the String into a series of bytes using the specified character set, and store the result in a new byte array

decoding:

  • String(byte[] bytes): Constructs a new String by decoding the specified byte array using the platform's default charset
  • String(byte[] bytes,String charsetName): Constructs a new String by decoding the specified byte array through the specified character set
import java.io.UnsupportedEncodingException;
import java.util.Arrays;

/*
编码:

- byte[] getBytes():使用平台的默认字符集将该String编码为以一系列字节,将结果存储到新的字节数组中
- byte[] getBytes(String charsetName):使用指定的字符集将该String编码为一系列字节,将结果存储到新的字节数组中

解码:

- String(byte[] bytes):通过使用平台的默认字符集解码指定的字节数组来构造新的String
- String(byte[] bytes,String charsetName):通过指定的字符集解码指定的字节数组来构造新的String

*/
public class StringDemo {
    
    
	public static void main(String[] args) throws UnsupportedEncodingException {
    
    
		//定义一个字符串
		String s="中国";
		//编码:
		//byte[] getBytes():使用平台的默认字符集将该String编码为以一系列字节,将结果存储到新的字节数组中
		byte[] bys = s.getBytes();//[-42, -48, -71, -6]
		
		//byte[] getBytes(String charsetName):使用指定的字符集将该String编码为一系列字节,将结果存储到新的字节数组中
//		byte[] bys = s.getBytes("UTF-8");//[-28, -72, -83, -27, -101, -67]
//		byte[] bys = s.getBytes("GBK");//[-42, -48, -71, -6]
		System.out.println(Arrays.toString(bys));
		
		//解码:
		//String(byte[] bytes):通过使用平台的默认字符集解码指定的字节数组来构造新的String
//		String ss=new String(bys);//中国
		//String(byte[] bytes,String charsetName):通过指定的字符集解码指定的字节数组来构造新的String
//		String ss=new String(bys,"UTF-8");//?й?
		String ss=new String(bys,"GBK");//中国
		System.out.println(ss);
	}
}

Running result:
insert image description here
Encoding and decoding problems in character streams

Character stream abstract base class:

  • Reader: an abstract class for character input streams
  • Writer: an abstract class for character output streams

Two classes related to encoding and decoding problems in character streams:

  • InputStreamReader: It is a bridge from byte stream to character stream.
    It reads bytes and decodes them into characters using the specified encoding. The
    character set it uses can be specified by name, can also be specified explicitly, or can receive the platform's default character set
  • OutputStreamWriter: It is a bridge from character stream to byte stream.
    It is a bridge from character stream to byte stream. It uses the specified encoding to encode the written characters into bytes. The
    character set it uses can be specified by name or can be specified explicitly. specified, or can receive the platform's default character set
import java.io.FileInputStream;
import java.io.FileOutputStream;
import java.io.IOException;
import java.io.InputStreamReader;
import java.io.OutputStreamWriter;

/*
- InputStreamReader:是从字节流到字符流的桥梁
	它读取字节,并使用指定的编码将其解码为字符
	它使用的字符集可以由名称指定,也可以被明确指定,或者可以接收平台的默认字符集

- OutputStreamWriter:是从字符流到字节流的桥梁
	是从字符流到字节流的桥梁,使用指定的编码将写入的字符编码为字节
	它使用的字符集可以由名称指定,也可以被明确指定,或者可以接收平台的默认字符集
*/
public class ConversionStreamDemo {
    
    
	public static void main(String[] args) throws IOException{
    
    
		//OutputStreamWriter(OutputStream out)创建一个使用默认字符编码的OutputStreamWriter
		//OutputStreamWriter(OutputStream out,String charsetName)创建一个使用命名字符集的OutputStreamWriter
		
//		FileOutputStream fos=new FileOutputStream("..\\hello java\\osw.txt");
//		OutputStreamWriter osw=new OutputStreamWriter(fos);
		//两步合并
//		OutputStreamWriter osw=new OutputStreamWriter(new FileOutputStream("..\\hello java\\osw.txt"));
//		OutputStreamWriter osw=new OutputStreamWriter(new FileOutputStream("..\\hello java\\osw.txt"),"GBK");//中国
		OutputStreamWriter osw=new OutputStreamWriter(new FileOutputStream("..\\hello java\\osw.txt"),"UTF-8");//涓浗
		osw.write("中国");
		osw.close();
		
		//InputStreamReader(InputStream in)创建一个使用默认字符集的InputStreamReader
		//InputStreamReader(InputStream in,String charsetName)创建一个使用命名字符集的InputStreamReader
		
//		InputStreamReader isr=new InputStreamReader(new FileInputStream("..\\hello java\\osw.txt"));//涓浗
//		InputStreamReader isr=new InputStreamReader(new FileInputStream("..\\hello java\\osw.txt"),"GBK");//涓浗
		InputStreamReader isr=new InputStreamReader(new FileInputStream("..\\hello java\\osw.txt"),"UTF-8");//中国
		//一次读取一个字符数据
		int ch;
		while((ch=isr.read())!=-1) {
    
    
			System.out.print((char)ch);
		}
		
		isr.close();
		
	}
}

Running results:
insert image description here
insert image description here
5 ways to write data in character stream

method name illustrate
void write(int c) write a character
void write(char[] cbuf) write a character array
void write(char[] cbuf,int off,int len) write part of character array
void write(String str) write a string
void write(String str,int off,int len) write part of a string
flush() Refresh the stream and continue to write data
close() Close the stream, freeing resources, but flushing the stream before closing. Once closed, data can no longer be written
import java.io.FileOutputStream;
import java.io.IOException;
import java.io.OutputStreamWriter;

/*
构造方法:
	OutputStreamWriter(OutputStream out)创建一个使用默认字符编码的OutputStreamWriter
	
	字符流写数据的5种方式**

	void write(int c)   写一个字符
	void write(char[] cbuf)写入一个字符数组
	void write(char[] cbuf,int off,int len)写入字符数组的一部分
	void write(String str)写一个字符串
	void write(String str,int off,int len)写一个字符串的一部分
*/

public class OutputStreamWriterDemo {
    
    
	public static void main(String[] args) throws IOException {
    
    
		//		OutputStreamWriter(OutputStream out)创建一个使用默认字符编码的OutputStreamWriter
		OutputStreamWriter osw = new OutputStreamWriter(new FileOutputStream("..\\hello java\\osw.txt"));
		/*
		//void write(int c)   写一个字符
		osw.write(97);//不刷新数据进不来,因为真正底层写数据是字节流,而字符流相对于字节流是有缓冲的
		//void flush()刷新流
		osw.flush();
		osw.write(98);
		osw.flush();
		osw.write(99);*/

		//void write(char[] cbuf)写入一个字符数组
		char[] chs = {
    
     'a', 'b', 'c', 'd', 'e' };
		//osw.write(chs);//abcde

		//void write(char[] cbuf,int off,int len)写入字符数组的一部分
		//osw.write(chs,0,chs.length);//abcde
		//osw.write(chs,1,3);//bcd

		//void write(String str)写一个字符串
		//osw.write("abcde");//abcde

		//void write(String str,int off,int len)写一个字符串的一部分
		//osw.write("abcde",0,"abcde".length());//abcde
		osw.write("abcde", 1, 3);//bcd

		osw.close();//关闭流,先刷新
		//osw.write(100);//java.io.IOException: Stream closed

	}
}

Two ways to read data by character stream

method name illustrate
int read() Read character data one at a time
int read(char[] cbuf) Read character array data one at a time

import java.io.FileInputStream;
import java.io.IOException;
import java.io.InputStreamReader;

/*
构造方法:
	InputStreamReader(InputStream in)创建一个使用默认字符集的InputStreamReader
	
字符流读数据的2种方式**
	int read()  一次读一个字符数据
	int read(char[] cbuf)一次读一个字符数组数据

*/
public class InputStreamReaderDemo {
    
    
	public static void main(String[] args) throws IOException{
    
    
		//InputStreamReader(InputStream in)创建一个使用默认字符集的InputStreamReader
//		InputStreamReader isr=new InputStreamReader(new FileInputStream("..\\hello java\\osw.txt"));
		InputStreamReader isr=new InputStreamReader(new FileInputStream("..\\hello java\\ConversionStreamDemo.java"));
		
		
		//int read()  一次读一个字符数据
//		int ch;
//		while((ch=isr.read())!=-1) {
    
    
//			System.out.print((char)ch);
//		}
		/*运行结果:
		hello
		world
		java*/
		
		//int read(char[] cbuf)一次读一个字符数组数据
		char[] chs=new char[1024];
		int len;
		while((len=isr.read(chs))!=-1) {
    
    
			System.out.print(new String(chs,0,len));
		}
		/*运行结果:
		hello
		world
		java*/
		
		//释放资源
		isr.close();
		
	}
}

operation result:
insert image description here
insert image description here

Case: copying Java files

Requirement: Copy "ConversionSteamDemo.java" in the module directory to "Copy.java" in the module directory

Ideas:

  1. Create a character input stream object from a data source
  2. Create a character output stream object according to the destination
  3. read and write data, copy files
  4. release resources
import java.io.FileInputStream;
import java.io.FileOutputStream;
import java.io.IOException;
import java.io.InputStreamReader;
import java.io.OutputStreamWriter;

/*
案例:复制Java文件
需求:把模块目录下的“ConversionSteamDemo.java”复制到模块目录下的“Copy.java”

思路:

 1. 根据数据源创建字输入流对象
 2. 根据目的地创建字符输出流对象
 3. 读写数据,复制文件
 4. 释放资源
*/

public class CopyJavaDemo {
    
    
	public static void main(String[] args) throws IOException {
    
    
		//1. 根据数据源创建字输入流对象
		InputStreamReader isr = new InputStreamReader(new FileInputStream("..\\hello java\\ConversionStreamDemo.java"));
		//2. 根据目的地创建字符输出流对象
		OutputStreamWriter osw = new OutputStreamWriter(new FileOutputStream("..\\hello java\\Copy.java"));
		//3. 读写数据,复制文件
		//一次读写一个字符数据
		//int ch;
		//while((ch=isr.read())!=-1) {
    
    
		//	osw.write(ch);
		//}

		//一次读写一个字符数组数据
		char[] chs = new char[1024];
		int len;
		while ((len = isr.read(chs)) != -1) {
    
    
			osw.write(chs, 0, len);
		}

		//释放资源
		isr.close();
		osw.close();

	}
}

operation result:
insert image description here
insert image description here

Case: copying Java files (improved version)

Requirement: Copy "ConversionSteamDemo.java" in the module directory to "Copy.java" in the module directory

analyze:

  1. The name of the conversion stream is relatively long, and our common operations are implemented according to the local default encoding. Therefore, in order to simplify writing, the conversion stream provides corresponding subclasses

  2. FileReader: Convenience class FileReader(String fileName) for reading character files
  3. FileWriter: Convenience class for writing character files
    FileWriter(String fileName)
  4. Analysis of data source and destination
    Data source: ...\hello java\ConversionStreamDemo.java—read data—Reader—InputStreamReader—FileReader
    destination:...\hello java\Copy.java—write data—Writer—OutputStreamWriter—FileWriter
import java.io.FileReader;
import java.io.FileWriter;
import java.io.IOException;

/*
案例:复制Java文件(改进版)

需求:把模块目录下的“ConversionSteamDemo.java”复制到模块目录下的“Copy.java”

分析:

 1. 转换流的名字比较长,而我们常见的操作都是按照本地默认编码实现的,所以,为了简化书写,转换流提供了对应的子类
 2. FileReader:用于读取字符文件的便捷类
	FileReader(String fileName)
 3. FileWriter:用于写入字符文件的便捷类
	FileWriter(String fileName)
 4. 数据源和目的地的分析
	数据源:---读数据---Reader---InputStreamReader---FileReader
	目的地:..\\hello java\\Copy.java--写数据--Writer--OutputStreamWriter---FileWriter

思路:

1. 根据数据源创建字输入流对象
2. 根据目的地创建字符输出流对象
3. 读写数据,复制文件
4. 释放资源

*/
public class CopyJavaDemo2 {
    
    
	public static void main(String[] args) throws IOException {
    
    
		//1. 根据数据源创建字输入流对象
		FileReader fr = new FileReader("..\\hello java\\ConversionStreamDemo.java");

		//2. 根据目的地创建字符输出流对象
		FileWriter fw = new FileWriter("..\\hello java\\Copy.java");

		//3. 读写数据,复制文件
		//一次读写一个字符数据
		//int ch;
		//while((ch=fr.read())!=-1) {
    
    
		//	fw.write(ch);
		//}

		//一次读写一个字符数组数据
		char[] chs = new char[1024];
		int len;
		while ((len = fr.read(chs)) != -1) {
    
    
			fw.write(chs, 0, len);
		}

		//4. 释放资源
		fr.close();
		fw.close();

	}
}

Running result:
insert image description here
insert image description here
character buffer stream

Character buffer stream:

  • BufferedWriter: Writes text to a character output stream, buffering characters to provide efficient writing of single characters, arrays, and strings, the buffer size can be specified, or a default size can be received. The default is large enough for most purposes
  • BufferedReader: Reads text from a character input stream, buffering characters to provide efficient reading of characters, arrays, and lines, the buffer size can be specified, or the default size can be used. The default is large enough for most purposes

Construction method:

  • BufferedWriter(Writer out)
  • BufferedReader(Reader in)

import java.io.BufferedReader;
import java.io.BufferedWriter;
import java.io.FileReader;
import java.io.FileWriter;
import java.io.IOException;

/*
字符缓冲流:

- BufferedWriter:将文本写入字符输出流,缓冲字符,以提供单个字符,数组和字符串的高效写入,可以指定缓冲区大小,或者可以接收默认大小。默认值足够大,可用于大多数用途
- BufferedReader:从字符输入流读取文本,缓冲字符,以提供字符,数组和行的高效读取,可以指定缓冲区大小,或者可以使用默认大小。默认值足够大,可用于大多数用途

构造方法:

- BufferedWriter(Writer out)
- BufferedReader(Reader in)
*/

public class BufferedStreamDemo2 {
    
    
	public static void main(String[] args) throws IOException {
    
    
		//BufferedWriter(Writer out)
		//		FileWriter fw=new FileWriter("..\\hello java\\bw.txt");
		//		BufferedWriter bw=new BufferedWriter(fw);
		/*
		//可合并为一句
		BufferedWriter bw=new BufferedWriter(new FileWriter("..\\hello java\\bw.txt"));
		
		bw.write("hello\r\n");
		bw.write("world\r\n");
		
		bw.close();*/

		//BufferedReader(Reader in)
		BufferedReader br = new BufferedReader(new FileReader("..\\hello java\\bw.txt"));
		/*
		//一次读一个字符数据
		int ch;
		while((ch=br.read())!=-1) {
			System.out.print((char)ch);
		}*/

		//一次读一个字符数组数据
		char[] chs = new char[1024];
		int len;
		while ((len = br.read(chs)) != -1) {
    
    
			System.out.print(new String(chs, 0, len));
		}

		br.close();

	}
}

operation result:
insert image description here

Case: Copying Java files (improved version of character buffer stream)

Requirement: Copy "ConversionSteamDemo.java" in the module directory to "Copy.java" in the module directory

Ideas:

  1. Create a character buffered input stream object based on the data source
  2. Create a character-buffered output stream object according to the destination
  3. read and write data, copy files
  4. release resources
import java.io.BufferedReader;
import java.io.BufferedWriter;
import java.io.FileReader;
import java.io.FileWriter;
import java.io.IOException;

/*
案例:复制Java文件(字符缓冲流改进版)

需求:把模块目录下的“ConversionStreamDemo.java”复制到模块目录下的“Copy.java”

思路:
	1. 根据数据源创建字符缓冲输入流对象
	2. 根据目的地创建字符缓冲输出流对象
	3. 读写数据,复制文件
	4. 释放资源
*/

public class CopyJavaDemo3 {
    
    
	public static void main(String[] args) throws IOException {
    
    
		//1. 根据数据源创建字符缓冲输入流对象
		BufferedReader br = new BufferedReader(new FileReader("..\\hello java\\ConversionStreamDemo.java"));

		//2. 根据目的地创建字符缓冲输出流对象
		BufferedWriter bw = new BufferedWriter(new FileWriter("..\\hello java\\Copy.java"));

		//3. 读写数据,复制文件
		/*
		//一次读写一个字符数据
		int ch;
		while((ch=br.read())!=-1) {
			bw.write(ch);
		}*/

		//一次读写一个字符数组数据
		char[] chs = new char[1024];
		int len;
		while ((len = br.read(chs)) != -1) {
    
    
			bw.write(chs, 0, len);
		}

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

	}
}

Running result:
insert image description here
insert image description here
the unique function of the character buffer stream

BufferedWrite:

  • void newLine(): Write a line of line separators, the line separator strings are defined by system properties

BufferedReader:

  • public String readLine(): Read a line of text. the result string containing the contents of the line, excluding any line termination characters, or null if the end of the stream has been reached

insert image description here

/*
字符缓冲流的特有功能

BufferedWrite:
	void newLine():写一行行分隔符,行分隔符字符串有系统属性定义

BufferedReader:
	public String readLine():读一行文字。结果包含行的内容的字符串,不包括任何行终止字符,如果流的结尾已经到大,则为null

*/

import java.io.BufferedReader;
import java.io.BufferedWriter;
import java.io.FileReader;
import java.io.FileWriter;
import java.io.IOException;

public class BufferedStreamDemo3 {
    
    
	public static void main(String[] args) throws IOException {
    
    
		/*//创建字符缓冲输出流
		BufferedWriter bw=new BufferedWriter(new FileWriter("..\\hello java\\bw.txt"));
		
		//写数据
		for(int i=0;i<10;i++) {
			bw.write("hello"+i);
		//			bw.write("\r\n");//只适用于Windows
			bw.newLine();
			bw.flush();
		} 
			hello0
			hello1
			hello2
			hello3
			hello4
			hello5
			hello6
			hello7
			hello8
			hello9
		
		//释放资源
		bw.close();
		*/

		//创建字符缓冲输入流
		BufferedReader br = new BufferedReader(new FileReader("..\\hello java\\bw.txt"));

		//public String readLine():读一行文字。结果包含行的内容的字符串,不包括任何行终止字符,如果流的结尾已经到大,则为null
		/*//第一次读取数据
		String line = br.readLine();
		System.out.println(line);//hello0
		//第二次读取数据
		line = br.readLine();
		System.out.println(line);//hello1
		//再多读两次
		line = br.readLine();
		System.out.println(line);//null
		line = br.readLine();
		System.out.println(line);//null
		*/

		String line;
		while ((line = br.readLine()) != null) {
    
    
			System.out.println(line);//readline只读内容,不包含换行符,要加ln
		}

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

	}
}

operation result:
insert image description here

Case: copying Java files (character buffer stream specific function improved version)

Requirement: Copy "ConversionSteamDemo.java" in the module directory to "Copy.java" in the module directory

Ideas:

  1. Create a character buffered input stream object based on the data source
  2. Create a character-buffered output stream object according to the destination
  3. Read and write data, copy files
    Use the unique function of character buffer stream
  4. release resources
import java.io.BufferedReader;
import java.io.BufferedWriter;
import java.io.FileReader;
import java.io.FileWriter;
import java.io.IOException;

/*
案例:复制Java文件(字符缓冲流特有功能改进版)

需求:把模块目录下的“ConversionSteamDemo.java”复制到模块目录下的“Copy.java”

思路:

 1. 根据数据源创建字符缓冲输入流对象
 2. 根据目的地创建字符缓冲输出流对象
 3. 读写数据,复制文件
 		使用字符缓冲流特有功能实现
 4. 释放资源
*/
public class CopyJavaDemo4 {
    
    
	public static void main(String[] args) throws IOException {
    
    
		//1. 根据数据源创建字符缓冲输入流对象
		BufferedReader br = new BufferedReader(new FileReader("..\\hello java\\ConversionStreamDemo.java"));

		//2. 根据目的地创建字符缓冲输出流对象
		BufferedWriter bw = new BufferedWriter(new FileWriter("..\\hello java\\Copy.java"));

		//3. 读写数据,复制文件(使用字符缓冲流特有功能实现)
		String line;
		while ((line = br.readLine()) != null) {
    
    
			bw.write(line);
			bw.newLine();//要加换行
			bw.flush();
		}

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

	}
}

operation result:
insert image description here
insert image description here

IO flow summary

insert image description here

Summary: byte stream can copy any file data, there are 4 ways to generally use byte buffer stream to read and write a byte array at a time

insert image description here

Summary: The character stream can only copy text data, there are 5 ways, generally using the unique function of the character buffer stream

Case: collection to file

Requirement: Write the string data in the ArrayList collection to a text file. Requirement: Each string element is used as a row of data in the file

Ideas:

  1. Create an ArrayList collection
  2. Store string elements in a collection
  3. Create a character buffered output stream object
  4. Traverse the collection to get each string data
  5. Call the method of the character buffer output stream object to write data
  6. release resources
import java.io.BufferedWriter;
import java.io.FileWriter;
import java.io.IOException;
import java.util.ArrayList;

/*
案例:集合到文件

需求:把ArrayList集合中的字符串数据写入到文本文件。

要求:每一个字符串元素作为文件中的一行数据

思路:

 1. 创建ArrayList集合
 2. 往集合中存储字符串元素
 3. 创建字符缓冲输出流对象
 4. 遍历集合,得到每一个字符串数据
 5. 调用字符缓冲输出流对象的方法写数据
 6. 释放资源
*/

public class ArrayListToTxtDemo {
    
    
	public static void main(String[] args) throws IOException {
    
    
		//1. 创建ArrayList集合
		ArrayList<String> array = new ArrayList<String>();

		//2. 往集合中存储字符串元素
		array.add("hello");
		array.add("world");
		array.add("java");

		//3. 创建字符缓冲输出流对象
		BufferedWriter bw = new BufferedWriter(new FileWriter("..\\hello java\\array.txt"));

		//4. 遍历集合,得到每一个字符串数据
		for (String s : array) {
    
    
			//5. 调用字符缓冲输出流对象的方法写数据
			bw.write(s);
			bw.newLine();
			bw.flush();

		}

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

	}
}

operation result:
insert image description here

Case: File to Collection

Requirements: Read the data in the text file into the collection and traverse the collection. Requirement: Each line of data in the file is a collection element

Ideas:

  1. Create a character buffered input stream object
  2. Create an ArrayList collection
  3. Call the method of the character buffer input stream object to read data
  4. Store the read string data into a collection
  5. release resources
  6. iterate through the collection
    insert image description here
import java.io.BufferedReader;
import java.io.FileReader;
import java.io.IOException;
import java.util.ArrayList;

/*
案例:文件到集合

需求:把文本文件中的数据读取到集合中,并遍历集合。要求:文件中每一行数据是一个集合元素

思路:

 1. 创建字符缓冲输入流对象
 2. 创建ArrayList集合
 3. 调用字符缓冲输入流对象的方法读数据
 4. 把读取到的字符串数据存储到集合中
 5. 释放资源
 6. 遍历集合 

*/
public class TxtToArrayListDemo {
    
    
	public static void main(String[] args) throws IOException {
    
    
		//1. 创建字符缓冲输入流对象
		BufferedReader br = new BufferedReader(new FileReader("..\\hello java\\array.txt"));

		//2. 创建ArrayList集合
		ArrayList<String> array = new ArrayList<String>();

		//3. 调用字符缓冲输入流对象的方法读数据
		String line;
		while ((line = br.readLine()) != null) {
    
    
			//4. 把读取到的字符串数据存储到集合中
			array.add(line);

		}

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

		//6. 遍历集合 
		for (String s : array) {
    
    
			System.out.println(s);
		}

	}
}

operation result:
insert image description here

Case: name roll

Requirement: There is a file that stores the names of classmates in the class, each name occupies one line, and it is required to implement a random roll caller through a program

Ideas:

  1. Create a character buffered input stream object
  2. Create an ArrayList collection object
  3. Call the method of the character buffer input stream object to read data
  4. Store the read string data into a collection
  5. release resources
  6. Use Random to generate a random number, the range of the random number is: [0, the length of the collection)
  7. Index the random number generated in step 6 into the ArrayList collection to get the value
  8. Output the data obtained in step 7 to the console

insert image description here

import java.io.BufferedReader;
import java.io.FileReader;
import java.io.IOException;
import java.util.ArrayList;
import java.util.Random;

/*
案例:点名器

需求:有一个文件里面存储了班级同学的姓名,每一个姓名占一行,要求通过程序实现随机点名器

思路:

 1. 创建字符缓冲输入流对象
 2. 创建ArrayList集合对象
 3. 调用字符缓冲输入流对象的方法读数据
 4. 把读取到的字符串数据存储到集合中
 5. 释放资源
 6. 使用Random产生一个随机数,随机数的范围在:[0,集合的长度)
 7. 把第6步产生的随机数最为索引到ArrayList集合中获取值
 8. 把第7步得到的数据输出在控制台 

*/
public class CallNameDemo {
    
    
	public static void main(String[] args) throws IOException {
    
    
		//1. 创建字符缓冲输入流对象
		BufferedReader br = new BufferedReader(new FileReader("..\\hello java\\array.txt"));

		//2. 创建ArrayList集合对象
		ArrayList<String> array = new ArrayList<String>();

		//3. 调用字符缓冲输入流对象的方法读数据
		String line;
		while ((line = br.readLine()) != null) {
    
    
			//4. 把读取到的字符串数据存储到集合中
			array.add(line);
		}

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

		//6. 使用Random产生一个随机数,随机数的范围在:[0,集合的长度)
		Random r = new Random();
		int index = r.nextInt(array.size());

		//7. 把第6步产生的随机数最为索引到ArrayList集合中获取值
		String name = array.get(index);

		//8. 把第7步得到的数据输出在控制台 

		System.out.println("幸运者是:" + name);

	}
}

operation result:
insert image description here

Case: collection to file (improved version)

Requirement: Write the student data in the ArrayList collection to a text file. Requirement: The data of each student object as a row of data in the file

Format: student number, name, age, place of residence
Example: 001, Xiaobai, 12, Beijing

Ideas:

  1. define student class
  2. Create an ArrayList collection
  3. create student object
  4. Add the student object to the collection
  5. Create a character buffered output stream object
  6. Traverse the collection to get each student object
  7. Concatenate the data of the student object into a string in the specified format
  8. Call the method of the character buffer output stream object to write data
  9. release resources

//1. 定义学生类
public class Student {
    
    
	private String number;//学号
	private String name;//姓名
	private int age;//年龄
	private String address;//居住地

	public String getNumber() {
    
    
		return number;
	}

	public void setNumber(String number) {
    
    
		this.number = number;
	}

	public String getName() {
    
    
		return name;
	}

	public void setName(String name) {
    
    
		this.name = name;
	}

	public int getAge() {
    
    
		return age;
	}

	public void setAge(int age) {
    
    
		this.age = age;
	}

	public String getAddress() {
    
    
		return address;
	}

	public void setAddress(String address) {
    
    
		this.address = address;
	}

	public Student(String number, String name, int age, String address) {
    
    
		super();
		this.number = number;
		this.name = name;
		this.age = age;
		this.address = address;
	}

	public Student() {
    
    
		super();
	}

}

import java.io.BufferedWriter;
import java.io.FileWriter;
import java.io.IOException;
import java.util.ArrayList;

/*
案例:集合到文件(改进版)

需求:把ArrayList集合中的学生数据写入到文本文件。要求:每一个学生对象的数据作为文件中的一行数据

格式:学号,姓名,年龄,居住地
举例:001,小白,12,北京

思路:

 1. 定义学生类
 2. 创建ArrayList集合
 3. 创建学生对象
 4. 把学生对象添加到集合
 5. 创建字符缓冲输出流对象
 6. 遍历集合,得到每一个学生对象
 7. 把学生对象的数据拼接成指定格式的字符串
 8. 调用字符缓冲输出流对象的方法写数据
 9. 释放资源

 */

public class ArrayListToTxtDemo2 {
    
    
	public static void main(String[] args) throws IOException {
    
    
		//2. 创建ArrayList集合
		ArrayList<Student> array = new ArrayList<Student>();

		//3. 创建学生对象
		Student s1 = new Student("001", "小白", 12, "北京");
		Student s2 = new Student("002", "小黑", 11, "上海");
		Student s3 = new Student("003", "小红", 15, "深圳");

		//4. 把学生对象添加到集合
		array.add(s1);
		array.add(s2);
		array.add(s3);

		//5. 创建字符缓冲输出流对象
		BufferedWriter bw = new BufferedWriter(new FileWriter("..\\hello java\\array.txt"));

		//6. 遍历集合,得到每一个学生对象
		for (Student stu : array) {
    
    
			//7. 把学生对象的数据拼接成指定格式的字符串
			StringBuilder sb = new StringBuilder();
			sb.append(stu.getNumber()).append(",").append(stu.getName()).append(",").append(stu.getAge()).append(",")
					.append(stu.getAddress());

			//8. 调用字符缓冲输出流对象的方法写数据
			bw.write(sb.toString());
			bw.newLine();
			bw.flush();

		}

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

	}
}

operation result:
insert image description here

Case: file to collection (improved version)

Requirements: Read the data in the text file into the collection and traverse the collection. Requirements: Each line of data in the file is a member variable value of a student object

Example: 001, Xiaobai, 12, Beijing

Ideas:

  1. define student class
  2. Create a character buffered input stream object
  3. Create an ArrayList collection
  4. Call the method of the character buffer input stream object to read data
  5. Split the read string data with split() to get a string array
  6. create student object
  7. Take each element in the string array and copy it to the member variable value of the student object
  8. Add the student object to the collection
  9. Release resources
    10. Traverse the collection

insert image description here

import java.io.BufferedReader;
import java.io.FileReader;
import java.io.IOException;
import java.util.ArrayList;

/*
案例:文件到集合(改进版)
需求:把文本文件中的数据读取到集合中,并遍历集合。

要求:文件中每一行数据是一个学生对象的成员变量值

举例:001,小白,12,北京

思路:

1. 定义学生类
2. 创建字符缓冲输入流对象
3. 创建ArrayList集合
4. 调用字符缓冲输入流对象的方法读数据
5. 把读取到的字符串数据用split()进行分割,得到一个字符串数组
6. 创建学生对象
7. 把字符串数组中的每一个元素取出来对应的复制给学生对象的成员变量值
8. 把学生对象添加到集合 
9. 释放资源
10.遍历集合

```java
//1. 定义学生类
public class Student {
	private String number;//学号
	private String name;//姓名
	private int age;//年龄
	private String address;//居住地

	public String getNumber() {
		return number;
	}

	public void setNumber(String number) {
		this.number = number;
	}

	public String getName() {
		return name;
	}

	public void setName(String name) {
		this.name = name;
	}

	public int getAge() {
		return age;
	}

	public void setAge(int age) {
		this.age = age;
	}

	public String getAddress() {
		return address;
	}

	public void setAddress(String address) {
		this.address = address;
	}

	public Student(String number, String name, int age, String address) {
		super();
		this.number = number;
		this.name = name;
		this.age = age;
		this.address = address;
	}

	public Student() {
		super();
	}

}

*/
public class FileToArrayListDemo { public static void main(String[] args) throws IOException { //2. Create character buffer input stream object BufferedReader br = new BufferedReader(new FileReader("…\hello java\array.txt")) ;


	//3. 创建ArrayList集合
	ArrayList<Student> array = new ArrayList<Student>();

	//4. 调用字符缓冲输入流对象的方法读数据
	String line;
	while (null != (line = br.readLine())) {
		//5. 把读取到的字符串数据用split()进行分割,得到一个字符串数组
		String[] strArray = line.split(",");
		//6. 创建学生对象
		Student s = new Student();

		//7. 把字符串数组中的每一个元素取出来对应的复制给学生对象的成员变量值
		s.setNumber(strArray[0]);
		s.setName(strArray[1]);
		s.setAge(Integer.parseInt(strArray[2]));//把字符串转成Integer类型的数据
		s.setAddress(strArray[3]);

		//8. 把学生对象添加到集合 
		array.add(s);
	}

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

	//10.遍历集合
	for (Student s : array) {
		System.out.println(s.getNumber() + "," + s.getName() + "," + s.getAge() + "," + s.getAddress());
	}

}

}


 运行结果:
 ![在这里插入图片描述](https://img-blog.csdnimg.cn/3970623cadc04c2f805850dcfa89171c.png)

## 案例:集合到文件(数据排序改进版)
需求:键盘录入5个学生信息(姓名,语文成绩,数学成绩,英语成绩)。要求按照成绩总分从高到低写入文本文件

格式:姓名,语文成绩,数学成绩,英语成绩 

举例:小白,89,99,78

思路:

 1. 定义学生类
 2. 创建TreeSet集合,通过比较器排序进行排序
 3. 键盘录入学生数据
 4. 创建学生对象,把键盘录入的数据对应赋值给学生对象的成员变量
 5. 把学生对象添加到TreeSet集合
 6. 创建字符缓冲输出流对象
 7. 遍历集合,得到每一个学生对象
 8. 把学生对象的数据拼接成指定格式的字符串
 9. 调用字符缓冲输出流对象的方法写数据
 10.释放资源

 

```java
import java.io.BufferedWriter;
import java.io.FileWriter;
import java.io.IOException;
import java.util.Comparator;
import java.util.Scanner;
import java.util.TreeSet;

/*
案例:集合到文件(数据排序改进版)
需求:键盘录入5个学生信息(姓名,语文成绩,数学成绩,英语成绩)。要求按照成绩总分从高到低写入文本文件

格式:姓名,语文成绩,数学成绩,英语成绩 

举例:小白,89,99,78

思路:

 1. 定义学生类
 2. 创建TreeSet集合,通过比较器排序进行排序
 3. 键盘录入学生数据
 4. 创建学生对象,把键盘录入的数据对应赋值给学生对象的成员变量
 5. 把学生对象添加到TreeSet集合
 6. 创建字符缓冲输出流对象
 7. 遍历集合,得到每一个学生对象
 8. 把学生对象的数据拼接成指定格式的字符串
 9. 调用字符缓冲输出流对象的方法写数据
 10.释放资源
*/

public class TreeSetToFileDemo {
	public static void main(String[] args) throws IOException {
		//2. 创建TreeSet集合,通过比较器排序进行排序
		TreeSet<Student2> tree = new TreeSet<Student2>(new Comparator<Student2>() {
			@Override
			public int compare(Student2 s1, Student2 s2) {
				//按照成绩总分从高到低
				int num = s2.getSum() - s2.getSum();
				//次要条件
				int num2 = num == 0 ? s1.getName().compareTo(s2.getName()) : num;
				return num2;
			};
		});

		//3. 键盘录入学生数据
		for (int i = 0; i < 5; i++) {
			Scanner sc = new Scanner(System.in);
			System.out.println("请录入第" + (i + 1) + "个学生的信息:");
			System.out.println("姓名:");
			String n = sc.nextLine();
			System.out.println("语文成绩:");
			int c = sc.nextInt();
			System.out.println("数学成绩:");
			int m = sc.nextInt();
			System.out.println("英语成绩:");
			int e = sc.nextInt();

			//4. 创建学生对象,把键盘录入的数据对应赋值给学生对象的成员变量
			Student2 s = new Student2();
			s.setName(n);
			s.setChanese(c);
			s.setMath(m);
			s.setEnglish(e);

			//5. 把学生对象添加到TreeSet集合
			tree.add(s);
		}

		//6. 创建字符缓冲输出流对象
		BufferedWriter bw = new BufferedWriter(new FileWriter("..\\hello java\\tree.txt"));

		//7. 遍历集合,得到每一个学生对象
		for (Student2 s : tree) {
			//8. 把学生对象的数据拼接成指定格式的字符串
			StringBuilder sb = new StringBuilder();
			sb.append(s.getName()).append(",").append(s.getChinese()).append(",").append(s.getMath()).append(",")
					.append(s.getEnglish());
			//9. 调用字符缓冲输出流对象的方法写数据
			bw.write(sb.toString());
			bw.newLine();
			bw.flush();

		}

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

		System.out.println("录入成功!");

	}
}

operation result:
insert image description here
insert image description here

Case: copying a single-level folder

Requirement: Copy the folder "E:\\itcast" to the module directory

Ideas:

  1. Create a data source directory File object, the path is E:\\itcast
  2. Get the name of the File object in the data source directory (itcast)
  3. Create a destination directory File object, the path name is composed of module name + itcast (…\\hello Java\\itcast)
  4. Determine whether the File corresponding to the destination directory exists, if not, create it
  5. Get the File array of all files in the data source directory
  6. Traverse the File array to get each File object, the File object is actually the data source file
    Data source file: E:\\itcast\\mn.jpg
  7. Get the name of the data source file File object (mn.jpg)
  8. Create a destination file File object, the path name is composed of destination directory + mn.jpg (…\\hello java\\mn.jpg)
  9. Copy files
    Since files are not only text files, but also pictures, videos and other files, copy files by byte way

insert image description here

import java.io.BufferedInputStream;
import java.io.BufferedOutputStream;
import java.io.File;
import java.io.FileInputStream;
import java.io.FileOutputStream;
import java.io.IOException;

/*
案例:复制单级文件夹
需求:把“E:\\\itcast”这个文件夹复制到模块目录下

思路:

 1. 创建数据源目录File对象,路径是E:\\\itcast
 2. 获取数据源目录File对象的名称(itcast)
 3. 创建目的地目录File对象,路径名是模块名+itcast组成(..\\\hello Java\\\itcast)
 4. 判断目的地目录对应的File是否存在,如果不存在,就创建
 5. 获取数据源目录下所有文件的File数组
 6. 遍历File数组,得到每一个File对象,该File对象,其实就是数据源文件
		数据源文件:E:\\\itcast\\\mn.jpg
 7. 获取数据源文件File对象的名称(mn.jpg)
 8. 创建目的地文件File对象,路径名是目的地目录+mn.jpg组成(..\\\hello java\\\mn.jpg)
 9. 复制文件
		由于文件不仅仅是文本文件,还有图片,视频等文件,所以采用字节路复制文件

 */

public class CopyFolderDemo {
    
    
	public static void main(String[] args) throws IOException {
    
    
		//1. 创建数据源目录File对象,路径是
		File srcFolder = new File("E:\\itcast");

		//2. 获取数据源目录File对象的名称(itcast)
		String srcFolderName = srcFolder.getName();

		//3. 创建目的地目录File对象,路径名是模块名+itcast组成()
		File destFolder = new File("..\\hello Java", srcFolderName);

		//4. 判断目的地目录对应的File是否存在,如果不存在,就创建
		if (!destFolder.exists()) {
    
    
			destFolder.mkdir();
		}

		//5. 获取数据源目录下所有文件的File数组
		File[] listFiles = srcFolder.listFiles();

		//6. 遍历File数组,得到每一个File对象,该File对象,其实就是数据源文件
		for (File srcFile : listFiles) {
    
    
			;
			//7. 获取数据源文件File对象的名称(mn.jpg)
			String srcFilename = srcFile.getName();
			//8. 创建目的地文件File对象,路径名是目的地目录+mn.jpg组成(..\\\hello java\\\mn.jpg)
			File destFile = new File(destFolder, srcFilename);
			//9. 复制文件
			copyFile(srcFile, destFile);

		}

	}

	private static void copyFile(File srcFile, File destFile) throws IOException {
    
    
		BufferedInputStream bis = new BufferedInputStream(new FileInputStream(srcFile));

		BufferedOutputStream bos = new BufferedOutputStream(new FileOutputStream(destFile));

		byte[] bys = new byte[1024];
		int len;
		while ((len = bis.read(bys)) != -1) {
    
    
			bos.write(bys, 0, len);
		}
		bis.close();
		bos.close();
	}
}

insert image description here

Case: copying multi-level folders

Requirement: Copy "E:\\itcast" to the F disk directory

Ideas:

  1. Create a data source File object, the path is E:\\itcast
  2. Create a destination File object, the path is F:\\
  3. The write method realizes the copy of the folder, and the parameters are the data source File object and the destination FIle object
  4. Determine whether the data source File is a directory
  • It is:
    1. Create a directory with the same name as the data source FIle under the destination
    2. Obtain the File array of all files or directories under the data source File
    3. Traverse the File array to get each File object
    4. Use the File as data Source File object, recursively call the method of copying folders
  • No,
    the description is a file, directly copied, using byte stream

insert image description here

import java.io.BufferedInputStream;
import java.io.BufferedOutputStream;
import java.io.File;
import java.io.FileInputStream;
import java.io.FileOutputStream;
import java.io.IOException;

/*
案例:复制多级文件夹
需求:把“E:\\itcast”复制到F盘目录下

思路:

 1. 创建数据源File对象,路径是E:\\itcast
 2. 创建目的地File对象,路径是F:\\
 3. 写方法实现文件夹的复制,参数为数据源File对象和目的地FIle对象
 4. 判断数据源File是否是目录
 	- 是:
		1.在目的地下创建和数据源FIle名称一样的目录
		2.获取数据源File下所有的文件或者目录的File数组
		3.遍历该File数组,得到每一个File对象
		4.把该File作为数据源File对象,递归调用复制文件夹的方法
 	- 不是
		说明是文件,直接复制,用字节流
*/

public class CopyFoldersDemo {
    
    
	public static void main(String[] args) throws IOException {
    
    
		//1. 创建数据源File对象,路径是E:\\itcast
		File srcFile = new File("E:\\itcast");
		//2. 创建目的地File对象,路径是F:\\
		File destFile = new File("F:\\");

		//3. 写方法实现文件夹的复制,参数为数据源File对象和目的地FIle对象
		copyFolder(srcFile, destFile);

	}

	//复制文件夹
	private static void copyFolder(File srcFile, File destFile) throws IOException {
    
    
		//4. 判断数据源File是否是目录
		if (srcFile.isDirectory()) {
    
    
			//1.在目的地下创建和数据源FIle名称一样的目录
			String srcFileName = srcFile.getName();
			File newFolder = new File(destFile, srcFileName);//F:\\itcast
			if (!newFolder.exists()) {
    
    
				newFolder.mkdir();
			}

			//2.获取数据源File下所有的文件或者目录的File数组
			File[] fileArray = srcFile.listFiles();

			//3.遍历该File数组,得到每一个File对象
			for (File file : fileArray) {
    
    
				//4.把该File作为数据源File对象,递归调用复制文件夹的方法
				copyFolder(file, newFolder);

			}

		} else {
    
    
			//说明是文件,直接复制,用字节流
			File newFile = new File(destFile, srcFile.getName());
			copyFile(srcFile, newFile);
		}

	}

	//字节缓冲流复制文件的方法
	private static void copyFile(File srcFile, File destFile) throws IOException {
    
    
		BufferedInputStream bis = new BufferedInputStream(new FileInputStream(srcFile));
		BufferedOutputStream bos = new BufferedOutputStream(new FileOutputStream(destFile));

		byte[] bys = new byte[1024];
		int len;
		while ((len = bis.read(bys)) != -1) {
    
    
			bos.write(bys, 0, len);
		}

		bis.close();
		bos.close();

	}
}

Running result:
insert image description here
exception handling of copied files

The practice of try...catch...finally:

try{
	可能出现异常的代码;
	}catch(异常类名 变量名){
		异常的处理代码;
	}finally{
		执行所有清除操作;
	}

JDK7 improvement plan:

try(定义流对象){
	可能出现异常的代码;
}catch(异常类名 变量名){
	异常的处理代码;
}

自动释放资源

Improvements to JDK9:

定义输入流对象;
定义输出流对象;
try(输入流对象;输出流对象){
	可能出现异常的代码;
}catch(异常类名 变量名){
	异常的处理代码;
}

自动释放资源

Demo code:

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

/*
复制文件加入异常处理
*/
public class CopyFileDemo {
    
    
	public static void main(String[] args) {
    
    

	}

	//JDK9的改进方案
	private static void method4() throws IOException {
    
    
		FileReader fr = new FileReader("fr.txt");
		FileWriter fw = new FileWriter("fw.txt");
		try (fr; fw) {
    
    

			char[] chs = new char[1024];
			int len;
			while ((len = fr.read()) != -1) {
    
    
				fw.write(chs, 0, len);
			}
		} catch (IOException e) {
    
    
			e.printStackTrace();
		}

	}

	//JDK7的改进方案
	private static void method3() {
    
    
		try (FileReader fr = new FileReader("fr.txt"); FileWriter fw = new FileWriter("fw.txt");) {
    
    

			char[] chs = new char[1024];
			int len;
			while ((len = fr.read()) != -1) {
    
    
				fw.write(chs, 0, len);
			}
		} catch (IOException e) {
    
    
			e.printStackTrace();
		}

	}

	//try...catch...finally
	private static void method2() {
    
    
		FileReader fr = null;//放外面定义,并给初始化
		FileWriter fw = null;
		try {
    
    
			fr = new FileReader("fr.txt");
			fw = new FileWriter("fw.txt");

			char[] chs = new char[1024];
			int len;
			while ((len = fr.read()) != -1) {
    
    
				fw.write(chs, 0, len);
			}

		} catch (IOException e) {
    
    
			e.printStackTrace();
		} finally {
    
    //close出现问题,先判断不为空,再用try...catch处理
			if (fw != null) {
    
    

				try {
    
    
					fw.close();
				} catch (IOException e) {
    
    
					// TODO Auto-generated catch block
					e.printStackTrace();
				}
			}
			//同理
			if (fr != null) {
    
    
				try {
    
    
					fr.close();
				} catch (IOException e) {
    
    
					// TODO Auto-generated catch block
					e.printStackTrace();
				}
			}

		}
	}

	//抛出异常
	private static void method1() throws IOException {
    
    
		FileReader fr = new FileReader("fr.txt");
		FileWriter fw = new FileWriter("fw.txt");

		char[] chs = new char[1024];
		int len;
		while ((len = fr.read()) != -1) {
    
    
			fw.write(chs, 0, len);
		}

		fr.close();
		fw.close();
	}

}

Guess you like

Origin blog.csdn.net/weixin_47678894/article/details/119734013