Vin*_*C M 23 java serialization effective-java
我正在阅读"Effective Java"中的序列化章节.我试图理解书中的下一段.
如果您实现的类具有可序列化和可扩展的实例字段,那么您应该注意这一点.如果类的实例字段初始化为其默认值(整数类型为零,布尔值为false,对象引用类型为null),则会违反不变量,必须将此readObjectNoData方法添加到类中:
// readObjectNoData for stateful extendable serializable classes
private void readObjectNoData() throws InvalidObjectException {
throw new InvalidObjectException("Stream data required");
}
Run Code Online (Sandbox Code Playgroud)
我不确定上述陈述的含义.
为了测试这个,我创建了一个Person类(可序列化和可扩展)
class Person implements Serializable{
private String name;
private int age;
Person() {
this("default",1);
}
Person(String name, int y) {
this.name = name;
this.age = y;
}
}
Run Code Online (Sandbox Code Playgroud)
以及扩展它的类Employee.
class Employee extends Person {
String address ;
public Employee()
{
super();
address ="default_address";
}
public Employee(String name , int age, String address)
{
super(name,age);
this.address = address;
}
}
Run Code Online (Sandbox Code Playgroud)
我创建的Person类中是否有任何不变量?什么时候会被侵犯?我复制粘贴了Employee类中的readObjectData()方法的代码,但它从未被调用过.何时调用readObject()方法?我错过了什么吗?
Mis*_*ble 22
Java对象序列化规范中的readObjectNoData部分看起来很有趣(见下文).
您对该问题的编辑提供了一个完美的例子.如果Employee是serialized,当它并未扩大Person,后来deserialized当它没有那么Person部分将被初始化为空字符串,0岁.使用此方法,您可以将它们分别初始化为"name"和1.
对于可序列化对象,readObjectNoData方法允许类在反序列化子类实例的情况下控制其自己字段的初始化,并且序列化流不会将所讨论的类列为反序列化对象的超类.如果接收方使用与发送方不同版本的反序列化实例的类,并且接收方的版本扩展了未由发送方版本扩展的类,则可能发生这种情况.如果序列化流已被篡改,也可能发生这种情况; 因此,尽管存在"恶意"或不完整的源流,readObjectNoData仍可用于正确初始化反序列化对象.
private void readObjectNoData() throws ObjectStreamException;每个可序列化的类可以定义自己的readObjectNoData方法.如果可序列化类没有定义readObjectNoData方法,那么在上面列出的情况下,类的字段将被初始化为它们的默认值(如JavaTM语言规范第二版第4.5.5节所列); 当引入对readObjectNoData方法的支持时,此行为与JavaTM 2 SDK,Standard Edition 1.4版之前的ObjectInputStream的行为一致.如果可序列化类确实定义了一个readObjectNoData方法并且出现了上述条件,则在反序列化期间将调用readObjectNoData,否则将调用类定义的readObject方法,如果该类已将该类列为流的超类正在反序列化的实例.
| 归档时间: |
|
| 查看次数: |
5617 次 |
| 最近记录: |