1.ObjectOutputStream(OOS)——>系列化输出流——>oos.writeObject(p);
系列化的对象所属的类:必须实现Serializable接口——>不重写任何方法
——>编译器会提示应当添加一个常量:serialVersionUID(想跨平台,必须声明版本号)
——>属性被transient修饰(序列化“瘦身”)
系列化的对象所属的类:
package day05;
import java.io.Serializable;
import java.util.Arrays;
/**
* 使用该类测试对象流对java中对象的读写操作
*
* VO Value Object
*
* 若一个类的实例希望被对象流读写,那么该类必须实现
* 接口:java.io.Serializable
* @author soft01
*
*/
public class Person implements Serializable{
/**
* 当一个类实现了Serializable接口后,
* 编译器会提示应当添加一个常量:serialVersionUID
* 这个常量标识当前类的序列化版本号。
* 若不指定编译器在编译当前类时会根据当前类的结构生成,
* 但是只要类的结构发生了变化,那么版本号就会改变。
*
* 版本号决定着一个对象是否可以反序列化成功。
* 当对象输入流在将一个对象进行反序列化时会检查该
* 对象的版本号与当前程序中这个类的版本号是否一致?
* 若一致:反序列化成功,若当前类发生了改变,那么则还原依然存在的属性。
* 若不一致,则反序列化方法readObject会抛出异常。
*/
private static final long serialVersionUID = 1L;
private String name;
private int age;
private String gender;
/*
* 当一个属性被transient修饰后,该属性在进行对象序化时其值会被忽略。
* 忽略不必要的属性值可以达到对象序列化“瘦身”的效果。
*/
private transient String[] otherInfo;
public Person() {
}
public Person(String name, int age, String gender, String[] otherInfo) {
super();
this.name = name;
this.age = age;
this.gender = gender;
this.otherInfo = otherInfo;
}
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 getGender() {
return gender;
}
public void setGender(String gender) {
this.gender = gender;
}
public String[] getOtherInfo() {
return otherInfo;
}
public void setOtherInfo(String[] otherInfo) {
this.otherInfo = otherInfo;
}
@Override
public String toString() {
return name+","+age+","+gender+","+Arrays.toString(otherInfo);
}
}
ObjectOutputStream(OOS):
package day05;
import java.io.FileOutputStream;
import java.io.IOException;
import java.io.ObjectOutputStream;
/**
* 对象流
* 对象流是一组高级流,作用是通过这组流可以方便的读写java中的任何对象。
* 对象输出流:用于写出对象,由于底层读写都是字节读写,
* 所以无论什么样的数据都要转换为字节才能写出。
* 对象输出流可以自行将给定的对象转换为一组字节然后写出。
* 省去了我们将对象按照结构转化为字节的麻烦。
* @author soft01
*
*/
public class ObjectOutputStream_writeObject {
public static void main(String[] args) throws IOException {
/*
* 将一个Person实例写入文件保存
*/
Person p = new Person();
p.setName("苍老师");
p.setAge(18);
p.setGender("女");
String[] otherInfo = {"hello","kity","lala"};
p.setOtherInfo(otherInfo);
System.out.println(p);
/*
* 文件输出流作用:将给定的字节写入到指定文件
*/
FileOutputStream fos = new FileOutputStream("person.obj");
/*
* 对象输出流作用:将给定的java对象转换为一组字节后写出
*/
ObjectOutputStream oos = new ObjectOutputStream(fos);
/*
* ObjectOutputStream提供了写对象的方法:
* void writeObject(Object obj)
* 该方法会将给定的对象转换为一组字节然后
* 通过其处理的流写出
*
* 这里的操作是先通过OOS将p对象转换为了一组字节,
* 然后再将该组字节通过FOS写入到了文件person.obj中
* 这里涉及到两个操作:
* 1:对象序列化,将一个对象按照结构转换为一组字节的过程
* 2:对象持久化,将该对象写入文件(硬盘中)的过程。
*/
oos.writeObject(p);
System.out.println("写出完毕!");
oos.close();
}
}
2.ObjectInputStream(OIS)——>反系列化输入流——>ois.readObject(p);
package day05;
import java.io.FileInputStream;
import java.io.IOException;
import java.io.ObjectInputStream;
/**
* 对象输入流
* 用于进行对象反序列化
* @author soft01
*
*/
public class ObjectInputStream_readObject {
public static void main(String[] args) throws ClassNotFoundException, IOException {
FileInputStream fis = new FileInputStream("person.obj");
ObjectInputStream ois = new ObjectInputStream(fis);
/*
* ObjectInputStream提供方法:
* Object readObject()
* 该方法可以读取字节并还原为指定的对象
* 需要确保OIS读取的字节是通过对象输出流(OOS)
* 将一个对象写出的字节.否则会抛出异常.
*/
Person p = (Person)ois.readObject();
System.out.println(p);
ois.close();
}
}