在java中实现readObject和writeObject方法以覆盖默认序列化时允许出现异常?

在java中实现readObject和writeObject方法以覆盖默认序列化时允许出现异常?,java,serialization,deserialization,Java,Serialization,Deserialization,我知道我们必须定义具有以下签名的方法来覆盖默认序列化过程: private void writeObject(ObjectOutputStream os) { } private void readObject(ObjectInputStream is) { } 对于上述方法可以引发的异常类型是否有任何限制?我知道方法引发的异常不是方法签名的一部分,但我想确认一下。您可以在这两种方法中引发任何RuntimeException 在writeObject(ObjectOutputStream o

我知道我们必须定义具有以下签名的方法来覆盖默认序列化过程:

private void writeObject(ObjectOutputStream os) {
}

private void readObject(ObjectInputStream is) {
}

对于上述方法可以引发的异常类型是否有任何限制?我知道方法引发的异常不是方法签名的一部分,但我想确认一下。

您可以在这两种方法中引发任何
RuntimeException

在writeObject(ObjectOutputStream out)中,还可以抛出
IOException

在readObject(ObjectInputStream In)中,yu还可以抛出
IOException
,并且
ClassNotFoundException

定义以下异常:

private void writeObject(java.io.ObjectOutputStream out)
    throws IOException
private void readObject(java.io.ObjectInputStream in)
    throws IOException, ClassNotFoundException;
private void readObjectNoData()
    throws ObjectStreamException;

这是调用write方法的地方:

        try {
            writeObjectMethod.invoke(obj, new Object[]{ out });
        } catch (InvocationTargetException ex) {
            Throwable th = ex.getTargetException();
            if (th instanceof IOException) {
                throw (IOException) th;
            } else {
                throwMiscException(th);
            }
        }

// ...

private static void throwMiscException(Throwable th) throws IOException {
    if (th instanceof RuntimeException) {
        throw (RuntimeException) th;
    } else if (th instanceof Error) {
        throw (Error) th;
    } else {
        IOException ex = new IOException("unexpected exception type");
        ex.initCause(th);
        throw ex;
    }
}
正如您所看到的,您可以抛出任何非运行时异常,它将被包装在IOException中,尽管您应该更喜欢IOException,因为它具有更短的堆栈跟踪和更有用的错误消息


我假设read方法也会被类似地调用,不过您可能想自己检查一下。

您从哪里得到“方法引发的异常不是方法签名的一部分”的错误印象,我是这样说的,因为我们不能根据方法抛出的检查异常类型重载方法,因此它不能是方法签名的一部分。仅仅因为不能基于检查异常重载,并不意味着签名中没有检查异常。您也不能基于返回类型重载,但这当然也是方法签名的一部分。@Tom感谢您消除了我的疑虑。现在已经很清楚了:)