Java I/o操作(三)
以下一小段(至分隔线之前)引自Think in Java 第四版第十章,作为复习
"10.1 输入和输出
可将Java库的IO类分割为输入与输出两个部分,这一点在用Web浏览器阅读联机Java类文档时便可知道。通过继承,从InputStream(输入流)衍生的所有类都拥有名为read()的基本方法,用于读取单个字节或者字节数组。类似地,从OutputStream衍生的所有类都拥有基本方法write(),用于写入单个字节或者字节数组。然而,我们通常不会用到这些方法;它们之所以存在,是因为更复杂的类可以利用它们,以便提供一个更有用的接口。因此,我们很少用单个类创建自己的系统对象。一般情况下,我们都是将多个对象重叠在一起,提供自己期望的功能。我们之所以感到Java的流库(Stream Library)异常复杂,正是由于为了创建单独一个结果流,却需要创建多个对象的缘故。
很有必要按照功能对类进行分类。库的设计者首先决定与输入有关的所有类都从InputStream继承,而与输出有关的所有类都从OutputStream继承."
-----------------------------------------------分隔------------------------------------------
Java的IO操作的复杂性正在于创建某一个类必须关联到其他的很多类,即一个流和一个流首尾相接,形成了一个类似管道的链接,这种模式是“装饰模式”的一个应用,英文名叫做Decorator.
例如:FileInputStream->BufferdInputStream->DataInputStream;
DataOutputStream->BuffedOutputStream->FileOutputStream;
-----------------------------------------------------------------------------------------------
Java.io.charset.*;
常用的字符集类别:
1.ASCII 是American Standard Code Information Interchange的所写,是美国信息交换标准代码,每个字符一个字节。常用0~127(十进制),这部分以0为第一位,其余部分表示特殊字符,为了区别和前面部分,用1开头。比较通用。
2.GB2312常用中文字编码,每个字符两个字节
3.GBK,完全兼容GB2312,并对繁体字和其他不常用字以及特殊符号进行编码;
字符的编码格式:
Unicode :为Java采用,每个字符表示为两个字节。
UTF-8:一种更加灵活的编码方式,根据字符的二进制数的大小来确定用多少个字节来表示该字符。
-------------------------------------------------------------------------------------------------
对字符流进行操作的Reader和Writer
Java统一使用Unicode对字符进行编码,每个字符占用两个字节,16位
InputStreamReader和OutputStreamWriter
InputStreamReade,从一个已经存在的InputStream对象构造
充当字节流转换为字符流的桥梁,可以在构造时指定解码规则(charset)
OutputStreamWriter,从一个已经存在的 OutputStream对象构造。
充当字符流转换为字节流的桥梁,可以在构造时指定编码规则(charset)
另引入一个概念:
将字符流转换为字节流成为编码,将字节流转换为字符流称为解码。
BufferedReader和BufferedWriter
提供带缓冲的读写,提高效率。分别从一个已经存在的Reader和Writer 构造。
------------------------------------------
注意:文字不能正确显示的问题一定是解码和编码规则不匹配。不同码之间的转换一般不可逆,比如采用两个字节的GB2312转换为采用一个字节的ASCII码会造成数据丢失。但是可以统一转换成字节码之后再进行相应字符流转换。
------------------------------------------
代码:
创建test.txt文件,并对其进行汉字录入。Import java.nio.charset.*;的意义在于可以解释 GB2312。
import java.io.*;
import java.nio.charset.*;
public class UnicodeTest
{
public static void main(String[] args) throws Exception
{
FileOutputStream fops=new FileOutputStream("test.txt");
OutputStreamWriter opsw=new OutputStreamWriter(fops,"GB2312");
BufferedWriter bw=new BufferedWriter(opsw);
InputStreamReader ipsr=new InputStreamReader(System.in,"GB2312");
BufferedReader br=new BufferedReader(ipsr);
String[] str=new String[10];
int i=0;
while(i<10)
{
str[i]=br.readLine();
i++;
if(i==10)
System.out.println("Enough now");
}
i=0;
while(i<10)
{
bw.write(str[i],0,str[i].length());
bw.flush();
bw.newLine();
System.out.println("Write line "+i+" completely");
i++;
}
}
}