Java 笔记 —— IO,java 定时任务 quartz 面试
这里的 InputStream in 参数,在创建对象时实际传入的是 InputStream 的具体实现类
package review.IO;
import java.io.BufferedInputStream;
import java.io.FileInputStream;
import java.io.IOException;
public class Demo4 {
public static void main(String[] args)throws IOException {
BufferedInputStream bis = new BufferedInputStream(new FileInputStream("a.txt"));
int len = 0;
byte[] bytes = new byte[1024];
while((len=bis.read(bytes))!=-1){
String s = new String(bytes,0,len);
System.out.println(s); //读取结果为 abcdefg
}
bis.close();
}
}
字节缓冲输出流 BufferedOutputStream
flush()的作用:刷新缓冲区,将缓冲区的内容写入到文件中
flush()与 close()的区别:
1、close()方法调用是关闭流对象,但是呢,会先刷新一次缓冲区,关闭之后,就不能继续使用该流对象了
2、flush()方法调用后,刷新一次缓冲区,但是流对象可以继续使用
使用缓冲输出流往文件里面写入数据的时候,flush 和 close 至少有一个才能将数据写入文件,否则数据将一直存在缓冲区,直到缓冲区满,然后自动写入
package review.IO;
import java.io.BufferedOutputStream;
import java.io.FileOutputStream;
import java.io.IOException;
public class Demo5 {
public static void main(String[] args) throws IOException {
BufferedOutputStream bos = new BufferedOutputStream(new FileOutputStream("b.txt"));
bos.write("你好,hello".getBytes());
//flush 将缓冲区里面的内容直接输出,而不用等待缓冲区满
bos.flush();
bos.close();
}
}
转换流
当文件内容中有中文的时候,如果我们只读取一个字节,然后输出这个字节,就会发现输出的结果是乱码
package review.IO;
import java.io.FileInputStream;
import java.io.IOException;
public class Demo6 {
public static void main(String[] args) throws IOException {
FileInputStream fis = new FileInputStream("a.txt");
int b = 0;
while((b=fis.read())!=-1){
System.out.print((char)b);
}
}
}
读取的结果为
是一串乱码,这是因为中文占用的字节数不止一个,多个字节才能组成一个中文汉字。如果单独拆出一个字节,就会发现输出的就是乱码
正因为这样,字节流操作中文很不方便,所以需要用到字符流
字符流是建立在字节流之上的,它能够提供字符层次的编码和解码
转换流为我们建立了字节流到字符流的桥梁,其本身是一种处理流,提供了字节流和字符流之间的转换。
Java 中提供了两个转换流:InputStreamReader 和 OutputStreamWriter,这两个类都属于字符流。
InputStreamReader 将字节输入流转为字符输入流,继承自 Reader。
OutputStreamWriter 是将字符输出流转为字节输出流,继承自 Writer。
在计算机中是以二进制的形式存储的数据,我们实际看到的文字信息都是讲二进制数据转换之后显示而来的。这两者之间存在着一种编码与解码的关系。
编码:类似与加密的过程,把能看懂的字符或字符串转成看不懂的字节。 String – byte[]
解码:类似于解密的过程,把看不懂的字节转成看得懂的字符或字符串。 byte[] – String
字符流其实可以理解为转换流。字符流=字节流+编码表。
package review.IO;
import java.io.IOException;
import java.util.Arrays;
public class Demo7 {
public static void main(String[] args) throws IOException {
String s = "你好世界";
//byte[] getBytes(Charset charset)
//使用给定的 charset 将该 String 编码为字节序列,将结果存储到新的字节数组中。
//String -- byte[]
byte[] bytes =s.getBytes("UTF-8");
System.out.println(Arrays.toString(bytes));
//String(byte[] bytes, Charset charset)
//构造一个新的 String 由指定用指定的字节的数组解码 charset
//byte[] -- String
String ss = new String(bytes,"UTF-8");
System.out.println(ss);
}
}
结果为
括号里面的 UTF-8 可以换成 Unicode 或者 GBK 等都可以,但是要注意编码和解码用的 charset 编码表要一样
字符输出流 OutputStreamWriter(字符转换流)
OutputStreamWriter 写数据方法
public void write(int c)
public void write(char[] cbuf)
public void write(char[] cbuf,int off,int len)
public void write(String str)
public void write(String str,int off,int len)
注意:从字符流开始,一次性读取一个字符数组,而不是一个字节数组。用 char[] 数组
package review.IO;
import java.io.FileOutputStream;
import java.io.IOException;
import java.io.OutputStreamWriter;
public class Demo8 {
public static void main(String[] args) throws IOException {
OutputStreamWriter osw = new OutputStreamWriter(new FileOutputStream("b.txt"));
//write(int c)
osw.write(97); //a
//write(char[] cbuf) 写入一个字符数组
char[] chars = {'a','b','c','d','e'};
osw.write(chars); //abcde
//write(char[] cbuf,int off,int len) 将字符数组中的一部分写到文件中
char[] chars1 = {'a','b','c','d','e'};
//从下标 1 开始读取两个字符
osw.write(chars1,1,2); //bc
//write(String str) 将字符串写入到文件中
osw.write("hello"); //hello
//write(String str,int off,int len) 将字符串的一部分写入到文件中
String s2 = "hadoop";
osw.write("hadoop",1,2); //ad
osw.flush();
osw.close();
}
}
字符输入流 InputStreamReader
InputStreamReader(InputStream in)
读取数据,根据默认的编码将字节流转换为字符流
创建一个使用默认字符集的 InputStreamReader。
InputStreamReader(InputStream in, String charsetName)
读取数据,根据指定的编码将字节流转换为字符流
创建一个使用指定字符集的 InputStreamReader。
读取数据的方法:
public int read():一次只读一个字符
public int read(char[] cbuf):一次读取一个字符数组
import java.io.FileInputStream;
import java.io.IOException;
import java.io.InputStreamReader;
public class Demo9 {
public static void main(String[] args) throws IOException {
//InputS
tream in = new FileInputStream("a.txt)
InputStreamReader isr = new InputStreamReader(new FileInputStream("a.txt"));
//一次只读取一个字符
int ch = 0;
while((ch=isr.read())!=-1){
System.out.println((char)ch);
}
isr.close();
}
}
结果为
可以发现控制台这里输出的是中文字符,而不再是 int 类型的数字
public class Demo9 {
public static void main(String[] args) throws IOException {
//InputStream in = new FileInputStream("a.txt)
InputStreamReader isr = new InputStreamReader(new FileInputStream("a.txt"));
//一次读取多个字符,也就是读取一个字符数组
char[] chars = new char[1024];
int len = 0;
while((len=isr.read(chars))!=-1){
System.out.println(new String(chars,0,len));
}
isr.close();
}
}
字符转换流的简便写法
字符流 = 字节流 + 编码表
OutputStreamWriter = FileOutputStream + 编码表(Unicode)
InputStreamReader = FileInputStream + 编码表(Unicode)
字符输出流 OutputStreamWriter 简便写法 FileWriter
字符输入流 InputStreamReader 简便写法 FileReader
package review.IO;
import java.io.FileReader;
import java.io.FileWriter;
import java.io.IOException;
public class Demo11 {
public static void main(String[] args) throws IOException {
FileReader fr = new FileReader("a.txt");
FileWriter fw = new FileWriter("b.txt");
int len = 0;
char[] chars = new char[1024];
while((len=fr.read(chars))!=-1){
fw.write(chars,0,len);
fw.flush();
}
fw.close();
fr.close();
}
}
结果成功将 a.txt 里面的内容写入到 b.txt 里面
注意:当程序中有多个流需要关闭的时候,按照从下到上的顺序关闭。
比如这里先打开的 fr,后打开的 fw。关闭的时候则先关 fw 后关 fr
字符缓冲输入流 BufferedReader
字符流为了高效读写,也提供了相对应的字符缓冲流
BufferedWriter:字符缓冲输出流
BufferedReader:字符缓冲输入流
BufferedReader(Reader in) 创建使用默认大小的输入缓冲区的缓冲字符输入流。
package review.IO;
import java.io.BufferedReader;
import java.io.FileReader;
import java.io.IOException;
public class Demo10 {
public static void main(String[] args) throws IOException {
BufferedReader br = new BufferedReader(new FileReader("a.txt"));
//一、一次读取一个字符
int ch = 0;
while((ch=br.read())!=-1){
System.out.println((char)ch);
}
//二、一次读取一个字符数组
int len = 0;
char[] chars = new char[1024];
while((len=br.read(chars))!=-1){
System.out.println(new String(chars,0,len));
}
br.close();
}
}
结果分别是(注意两段代码要分开运行,否则第二段代码读取内容为空,这里是为了直观所以放在了一起)
字符缓冲输出流 BufferedWriter
BufferedWriter:字符缓冲输出流
将文本写入字符输出流,缓冲字符,以提供单个字符,数组和字符串的高效写入。
可以指定缓冲区大小,或者可以接受默认大小。
默认值足够大,可用于大多数用途。
创建方式:
BufferedWriter(Writer out) 创建使用默认大小的输出缓冲区的缓冲字符输出流
BufferedWriter(Writer out, int sz) 创建一个新的缓冲字符输出流,使用给定大小的输出缓冲区。
package review.IO;
import java.io.BufferedWriter;
import java.io.FileWriter;
import java.io.IOException;
public class Demo12 {
public static void main(String[] args) throws IOException {
/*
BufferedWriter bw = new BufferedWriter(
new OutputStreamWriter(new FileOutputStream("b.txt)));
这是原来的写法,实在复杂,需要创建一个字节输出流 FileOutputStream
然后用 OutputStreamWriter 将字节输出流转为字符输出流
再将字符输出流添加上缓冲区的功能变成 BufferedWriter
*/
BufferedWriter bw = new BufferedWriter(new FileWriter("b.txt"));
bw.write(97); //a
bw.write(98); //b
bw.write("hello"); //hello
bw.write("hadoop",1,2); //ad
char[] chars = {'a','b','c','d'};
bw.write(chars); //abcd
bw.write(chars,1,2); //bc
bw.flush();
bw.close();
}
}
评论