Java中的输入是指从数据源等读到Java程序中,这里的数据源可以是文件,内存或网络连接,输出则是指从Java程序中写到目的地。
输入输出流可以分为以下几种类型(暂时不考虑File类)
类名 | 中文名 |
---|---|
InputStream |
字节输入流 |
OutputStream |
字节输出流 |
Reader |
字符输入流 |
Writer |
字符输出流 |
Java IO共涉及40多个类,下图是字节流各个类之间的关系
InputStream
InputStream的子类及其说明有如下所示
名称 | 说明 |
---|---|
BufferedInputStream |
为另一个输入流添加一些功能,即缓冲输入以及支持 mark 和 reset 方法的能力。 |
ByteArrayInputStream |
包含一个内部缓冲区,该缓冲区包含从流中读取的字节。 |
DataInputStream |
数据输入流允许应用程序以与机器无关方式从底层输入流中读取基本 Java 数据类型。 |
FileInputStream |
从文件系统中的某个文件中获得输入字节。 |
FilterInputStream |
包含其他一些输入流,它将这些流用作其基本数据源,它可以直接传输数据或提供一些额外的功能。 |
ObjectInputStream |
对以前使用 ObjectOutputStream 写入的基本数据和对象进行反序列化。 |
PipedInputStream |
管道输入流应该连接到管道输出流;管道输入流提供要写入管道输出流的所有数据字节。 |
PushbackInputStream |
为另一个输入流添加性能,即“推回 (push back)”或“取消读取 (unread)”一个字节的能力。 |
SequenceInputStream |
表示其他输入流的逻辑串联。 |
OutputStream
OutputStream的子类及其说明有如下所示
名称 | 说明 |
---|---|
BufferedOutputStream |
该类实现缓冲的输出流。 |
ByteArrayOutputStream |
此类实现了一个输出流,其中的数据被写入一个 byte 数组。 |
DataOutputStream |
数据输出流允许应用程序以与机器无关方式将基本 Java 数据类型写入输出流中。 |
FileOutputStream |
文件输出流是用于将数据写入 File 或 FileDescriptor 的输出流。 |
FilterOutputStream |
此类是过滤输出流的所有类的超类。 |
ObjectOutputStream |
ObjectOutputStream 将 Java 对象的基本数据类型和图形写入 OutputStream。 |
PipedOutputStream |
可以将管道输出流连接到管道输入流来创建通信管道。 |
PrintStream |
为其他输出流添加了功能,使它们能够方便地打印各种数据值表示形式。 |
对于类中方法的熟悉不详述了,可以参照JDK文档,或者可以试着在IDE中,实例化上面的类,使用此类对象时,按下.之后,会出现提示框,再一个一个熟悉就好了。
简单示例
了解了常用的字节流类,下面以文件数据的输入输出说明以上类的使用。
1.在java程序中生成1~20的平方数,并输出到文件中。
package com.songpu;
import java.io.BufferedOutputStream;
import java.io.FileOutputStream;
import java.io.IOException;
import java.io.PrintStream;
public class MyFileOutputStream {
public static void main (String[] args) throws IOException{
try{
FileOutputStream fos = new FileOutputStream("F:\\test1.txt");
BufferedOutputStream bos = new BufferedOutputStream(fos,1024);
PrintStream ps = new PrintStream(bos,false);
System.setOut(ps);
for(int i= 0;i<20;i++){
System.out.println(i*i);
}
ps.close();
bos.close();
fos.close();
}catch(IOException e){
e.printStackTrace();
}
}
}
2.将刚才生成的文件中的数据输入到程序,并将其打印到屏幕
package com.songpu;
import java.io.*;
public class MyFlieInputStream {
public static void main(String[] args) throws IOException {
File file = new File("F:\\test1.txt");
FileInputStream in = new FileInputStream(file);
BufferedInputStream bis = new BufferedInputStream(in);
byte[] bytes = new byte[(int) file.length()];
do {
bis.read(bytes);
System.out.println(new String(bytes));
}while (bis.read() != -1);
bis.close();
in.close();
}
}
再以序列化与反序列化的例子说明ObjectInputStream和ObjectOutputStream的使用
Java序列化是将对象变成二进制形式的一连串字符描述的过程,反序列化就是序列化的相反过程,把这些字符重建为对象。
序列化和反序列化的作用,是保存对象到文件或数据库中,使对象能够传输,序列化的要求是实现Serializable接口,代码如下所示
package com.songpu.serial;
import java.io.FileInputStream;
import java.io.FileOutputStream;
import java.io.IOException;
import java.io.ObjectInputStream;
import java.io.ObjectOutputStream;
import java.io.OutputStream;
import java.io.Serializable;
/*
* 待序列化的类,实现序列化接口
*/
class Person implements Serializable{
public String name;
public int age;
public Person(String name, int age) {
//super();
this.name = name;
this.age = age;
}
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 class SerialTest{
public static void main(String[] args) throws IOException, ClassNotFoundException{
ObjectOutputStream oos = new ObjectOutputStream(new FileOutputStream("F:\\test.txt"));
Person p0 = new Person("tangsong",21);
oos.writeObject(p0);
oos.flush();
oos.close();
deserial();
}
public static void deserial() throws ClassNotFoundException, IOException{
ObjectInputStream ois = new ObjectInputStream(new FileInputStream("F:\\test.txt"));
Person p1 = (Person)ois.readObject();
ois.close();
System.out.println("Name="+p1.getName()+";Age="+p1.getAge());
}
}
运行上述代码的结果如下: