IO流。按照流的方向可以分为输入流和输出流。输入流:是按程序来说的。比如文件到程序。输出流:程序到文件。输入流和输出流分别通过抽象类InputStream和OutputStream来实现。同时,为了处理Unicode字符串,还定义了单独的类,这些类从Reader和Writer继承而来。
首先,字节流。。。。
一、InputStream。用于从源按字节读取数据。它提供的读取方法有:
1、read():读取一个字节
2、read(byte[] b):读取一个字节数组
3、read(byte[] b,int offset,int len):读取一个字节数组,放到数组起始位置在offset。并用len表示读取的最大长度。
二、OutputStream。对应于输入流,方法有:
1、write(int c):写一个字节到流中。
2、write(byte[] b):写一个字节数组。
3、write(byte[] b,int offset,int len):将一个数组从offset开始的len个字节写入流中。
public static void main(String[] args) throws Exception{ InputStream is=new FileInputStream("d://test//vi.txt"); OutputStream os=new FileOutputStream("d://test//TT.txt"); int i=0; while((i=is.read())!=-1){ os.write(i); } is.close(); os.close(); }
运行代码,在d盘test文件夹中自动生成TT.txt打开会看到与vi.txt相同的内容。但是你会发现无论你运行多少遍,TT.txt里的内容只出现一次,如果我们将3出的代码改为:
OutputStream os=new FileOutputStream("d://test//TT.txt",true) ;每一次,都会在源文件的尾部追加内容。
注意:1、代码中的close()方法,这个是必须的,每次用完都要进行关闭操作。
2、FileInputStream和OutPutStream用于从文件中读取信息和写入信息。它们是InputStream和OutputStream的子类。
好了,下面介绍包装流。包装流对低级流进行了封装,并扩展了基本流的功能。
一、BufferedInputStream/BufferedOutputStream。带有缓冲的过滤流。在读写的时候对数据进行缓存。避免了每次存取都要与物理设备进行交互。使用BufferedOutputStream输出时,数据线输入到缓冲区,可以调用flush()方法让缓冲区内容写入。
public static void main(String[] args) throws IOException { FileInputStream is=new FileInputStream("d://commons.rar"); BufferedInputStream bis=new BufferedInputStream(is); FileOutputStream os=new FileOutputStream("d://copys.rar"); BufferedOutputStream bos=new BufferedOutputStream(os); int b=0; while((b=bis.read())!=-1){ bos.write(b); } bos.flush();}
二、DataInputStream和DataOutputStream。分别继承
public static void main(String[] args) throws Exception { FileOutputStream fos=new FileOutputStream("d://mi.doc"); DataOutputStream dos=new DataOutputStream(fos); dos.writeUTF("hello"); FileInputStream fis=new FileInputStream("d://vi.txt"); DataInputStream dis=new DataInputStream(fis); String s=dis.readUTF(); System.out.println(s); dos.close(); dis.close();}
我们说过,对于unicode字符集,为它的处理引入了Writer和Reader抽象类。
一、InputStreamReader/OutputStreamWriter
FileInputStream fis=new FileInputStream(new File("d://vi.txt"));InputStreamReader isr=new InputStreamReader(fis,"utf-8");char c=(char)isr.read();System.out.println(c); FileOutputStream fos=new FileOutputStream(new File("d://vi.txt"));OutputStreamWriter osw=new OutputStreamWriter(fos,"utf-8");osw.write("你好");isr.close();osw.close();
按照指定字符集读取。
二、FileReader/FileWriter
FileReader fr=new FileReader(new File("d://vi.txt"));char c=(char)fr.read();System.out.println(c);FileWriter fw=new FileWriter(new File("d://vi.txt"));fw.write("toy tidy\r\n");fw.write("wuwa");fr.close();fw.close();
三、BufferedReader/BufferedWriter
FileInputStream fis=new FileInputStream(new File("d://vi.txt"));InputStreamReader isr=new InputStreamReader(fis);BufferedReader br=new BufferedReader(isr);String s=br.readLine();System.out.println(s);FileOutputStream fos=new FileOutputStream(new File("d://vi.txt"));OutputStreamWriter osw=new OutputStreamWriter(fos);BufferedWriter bw=new BufferedWriter(osw);bw.write("two bird");bw.newLine();bw.write("fly away");br.close();bw.close();
最后,我要说的就是;对象序列化:有时我们需要将内存堆区中的对象保存到文件中二进制数据,还需要将文件中的二进制数据再读到内存中。注意事项:
1. 一个对象想序列化,需要实现可序列化接口。Serializable接口,没有字段,没有方法,只是标志接口,用于说明对象可以被序列化了。
2. static或transient修饰的属性不被序列化。
3. 相关对象都需要实现Serializable接口。
4. 多个对象的序列化借助于集合。
public class Person implements Serializable{private String name;private int age;/*setter/getter方法toString/hashCode/equals方法*/}
public class TestSeriaPer2 {public static void main(String[] args) throws Exception { Person p=new Person("gugu",21); Person p2=new Person("hhh",21); Listlist=new ArrayList (); list.add(p); list.add(p2); File file=new File("d://person.txt"); FileOutputStream fos=new FileOutputStream(file); ObjectOutputStream oos=new ObjectOutputStream(fos); oos.writeObject(list); FileInputStream fis=new FileInputStream(file); ObjectInputStream ois=new ObjectInputStream(fis); List perlist= (List ) ois.readObject(); for(Person pp:perlist){ System.out.println(pp); } ois.close(); oos.close();}}
完成了。。。。。。(中国的省略号)