Java:writeObject与writeExternal的效率

据说Java的默认序列化机制效率不高,因为a)它发现通过reflection写入/读取的字段通常很慢b)它将额外的数据写入流。

提高效率的一种方法是实现Externalizable及其writeExternal / readExternal方法。

这是一个问题:如果我改为提供’writeObject / readObject’方法并且不在其中调用deafiltWriteObject / defaultReadObject,那么这个机制将不会使用reflection来确定要写入/读取的字段,而且它不会写入额外的要流式传输的数据(还是不确定)? 那么从效率的角度来看,实现上面提到的writeObject / readObject与实现Externalizable一样吗? 或者后一种选择是否会带来一些前者不具备的实际效益?

编辑:当然,差异是当实现readObject / writeObject的Serializable类被子类化时,如果子类有自己的readObject / writeObject,则它们不需要调用super的readObject / writeObject。 如果超级/子类改为实现Externalizable,则不是这样。 在这种情况下,需要显式调用super的writeExternal / readExternal。 然而,从效率的角度来看,这种差异是无关紧要的。

在选择下一个要调用的类/ writeObject / readObject时,仍有一些问题。 但它显着减少了。

这可以与Externalizable执行相同的操作,具体取决于您正在执行的操作以及是否使用它为您提供的额外选项。 例如,readObject假定您每次都创建一个新对象,Externalizable具有readResolve,这意味着您可以重用对象。

http://docs.oracle.com/javase/1.5.0/docs/guide/serialization/spec/input.html

在许多情况下,回收对象是加速反序列化的“下一步”。 (假设这是你的选择)

http://vanillajava.blogspot.co.uk/2011/10/recycling-objects-to-improve.html

在尝试和完成序列化机制的代码时发现了一些东西:

1)如果发现对象是Externalizable,则将其强制转换为Externalizable,并在其上调用相应的方法; 而对于Serializable对象,reflection性地检查它是否具有readObject / writeObject。 所以也许这会让它稍慢一点,

2)为Externalizable写的数据量比使用readObject / writeObject的Serializable少一点(当我写B的对象时,我发现以下代码的差异为1个字节)。

对于Externalizable:

static class A implements Externalizable { @Override public void writeExternal(ObjectOutput out) throws IOException { System.out.println("A write called"); } @Override public void readExternal(ObjectInput in) throws IOException, ClassNotFoundException { System.out.println("A read called"); } } static class B extends A implements Externalizable { @Override public void writeExternal(ObjectOutput out) throws IOException { super.writeExternal(out); System.out.println("B write called"); } @Override public void readExternal(ObjectInput in) throws IOException, ClassNotFoundException { super.readExternal(in); System.out.println("B read called"); } } 

对于Serializable:

 static class A implements Serializable { private void writeObject(ObjectOutputStream out) throws IOException { System.out.println("A write called"); } private void readObject(ObjectInputStream in) throws IOException, ClassNotFoundException { System.out.println("A read called"); } } static class B extends A implements Serializable { private void writeObject(ObjectOutputStream out) throws IOException { System.out.println("B write called"); } private void readObject(ObjectInputStream in) throws IOException, ClassNotFoundException { System.out.println("B read called"); } } 

类设计方面的主要区别在于Serializable可以在任何类上工作,而Externalizable仅适用于具有公共默认(无参数)构造函数的可变类。