给我java.lang.ClassCastException:slz.A无法转换为slz.B为什么?这两个类具有相同的字段和方法。为什么我在反序列化时无法将类型A的序列化对象转换为类型B?
public class A implements Serializable {
private String var1;
private String var2;
private static final long serialVersionUID = 4L;
public String getVar1() {
return var1;
}
public void setVar1(String var1) {
this.var1 = var1;
}
public String getVar2() {
return var2;
}
public void setVar2(String var2) {
this.var2 = var2;
}
}
public class B implements Serializable {
private String var1;
private String var2;
private static final long serialVersionUID = 4L;
public String getVar1() {
return var1;
}
public void setVar1(String var1) {
this.var1 = var1;
}
public String getVar2() {
return var2;
}
public void setVar2(String var2) {
this.var2 = var2;
}
@Override
public String toString() {
return var1 + " " + var2;
}
}
public class Test {
public static void main(String[] args) {
A a = new A();
a.setVar1("d");
a.setVar2("e");
B b = null;
try(FileOutputStream fileOut = new FileOutputStream("Test.ser");
ObjectOutputStream outputStream = new ObjectOutputStream(fileOut);
FileInputStream inputStream = new FileInputStream("Test.ser");
ObjectInputStream objectInputStream = new ObjectInputStream(inputStream);){
outputStream.writeObject(a);
b = (B) objectInputStream.readObject();
} catch (FileNotFoundException e) {
e.printStackTrace();
} catch (IOException e) {
e.printStackTrace();
} catch (ClassNotFoundException e) {
e.printStackTrace();
}
}
}
两个类A和B实现可序列化,它们具有相同的字段和方法以及相同的序列号ID
答案 0 :(得分:3)
毕竟它们是不同的类。在序列化期间,该过程将需要跟踪其类型,因为在反序列化期间,运行时需要知道要实例化哪种类型。当类型不匹配时,您将获得类强制转换异常。
但是,您应该研究readResolve()
方法,该方法将在反序列化期间调用,并且可用于创建与流不同的类型。如果您将以下方法添加到类A中,则反序列化将起作用:
public Object readResolve() throws ObjectStreamException{
return new B();
}
从Javadocs的Serializable接口中:
* <p>Serializable classes that need to designate an alternative object to be
* used when writing an object to the stream should implement this
* special method with the exact signature:
*
* <PRE>
* ANY-ACCESS-MODIFIER Object writeReplace() throws ObjectStreamException;
* </PRE><p>
*
* This writeReplace method is invoked by serialization if the method
* exists and it would be accessible from a method defined within the
* class of the object being serialized. Thus, the method can have private,
* protected and package-private access. Subclass access to this method
* follows java accessibility rules. <p>
*
* Classes that need to designate a replacement when an instance of it
* is read from the stream should implement this special method with the
* exact signature.
*
* <PRE>
* ANY-ACCESS-MODIFIER Object readResolve() throws ObjectStreamException;
* </PRE><p>
*
* This readResolve method follows the same invocation rules and
* accessibility rules as writeReplace.<p>
答案 1 :(得分:2)
您不能反序列化A到B,因为它们是不同的类。它们实际上是相同的没关系,但它们仍然是不同的类。就像试图将狗反序列化为猫一样,它们的腿数相同,但是它们是不同的动物。
答案 2 :(得分:-1)
public class A extends B {}
将您的A类更改为上面的代码,这应该可以工作。发生类强制转换异常是因为您的类A和B都不属于同一类型。反序列化过程返回,对象类型为A,而您试图将其强制转换为B,这就是失败的原因。