java:使用对象流完成集合的序列化和反序列化
java中提供了一种对象序列化的机制,可以将对象和字节序列之间进行转换:
- 序列化 程序中,可以用一个字节序列来表示一个对象,该字节序列包含了对象的类型、对象中的数据等。
如果这个字节序列写出到文件中,就相当于在文件中持久保存了这个对象的信息 - 反序列化 相反的过程,从文件中将这个字节序列读取回来,在内存中重新生成这个对象,对象的类型、对象中的数据等,都和之前的那个对象保持一致。(注意,这时候的对象和之前的对象,内存地址可能是不同的)
对象流
ObjectInputStream 和 ObjectOutputStream
java.io.ObjectOutputStream:将Java对象转换为字节序列,并输出到内存、文件、网络等地方
注意,具体输出到什么地方,要看 ObjectOutputStream “包裹”的是哪一个节点流
java.io.ObjectInputStream:从某一个地方读取出对象的字节序列,并生成对应的对象。
在java中,并非所有对象都可以进行序列化和反序列化,而是只有实现了指定接口的对象才可以进行。
java.io.Serializable 接口
Serializable 接口给需要序列化的类,提供了一个序列版本号:
serialVersionUID
该版本号的目的,是用于验证序列化的对象和对应类是否版本匹配
默认情况下,每次修改代码编译生成的新的class文件中,都会根据当前类的信息计算出一个序列化版本号,之前序列化的字节中的保存的是之前老的版本号,和现在这个新的不一致,然后就会报错
举例:
序列化:
import java.io.Serializable;
/*
* 要想对象实现序列化 需要满足以下要求
*
* 1、需要实现接口 Serializeble
* 2、添加序列化版本号 提供一个全局变量 serialVersionUID
* 3、除了当前Person类需要实现Serializable接口之外,还必须保证其内部所属性
* 也必须是可序列化的。(默认情况下,基本数据类型可序列化)
*
* 补充:ObjectOutputStream和ObjectInputStream不能序列化static和transient修饰的成员变量
*
* */
public class Person implements Serializable{
public static final long SerialVersionUID=4723343L;
private String name;
private int 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;
}
@Override
public String toString() {
return "Person{" +
"name='" + name + '\'' +
", age=" + age +
'}';
}
public Person(String name, int age) {
this.name = name;
this.age = age;
}
public Person() {
}
}
序列化代码实现:
@Test
public void testObjectOutputStream(){
ObjectOutputStream oos = null;
try {
//1.
oos = new ObjectOutputStream(new FileOutputStream("object.dat"));
//2.
oos.writeObject(new String("我爱北京天安门"));
oos.flush();//刷新操作
oos.writeObject(new Person("陈奕迅",23));
oos.flush();
oos.writeObject(new Person("周杰伦",23,1001,new Account(5000)));
oos.flush();
} catch (IOException e) {
e.printStackTrace();
} finally {
if(oos != null){
//3.
try {
oos.close();
} catch (IOException e) {
e.printStackTrace();
}
}
}
}
反序列化:
@Test
public void testObjectInputStream(){
ObjectInputStream ois = null;
try {
ois = new ObjectInputStream(new FileInputStream("object.dat"));
Object obj = ois.readObject();
String str = (String) obj;
Person p = (Person) ois.readObject();
Person p1 = (Person) ois.readObject();
System.out.println(str);
System.out.println(p);
System.out.println(p1);
} catch (IOException e) {
e.printStackTrace();
} catch (ClassNotFoundException e) {
e.printStackTrace();
} finally {
if(ois != null){
try {
ois.close();
} catch (IOException e) {
e.printStackTrace();
}
}
}
}
重新写了个例子,之前写的例子不太标准。