正文
bout.writeShort(STREAM_MAGIC);
bout.writeShort(STREAM_VERSION);
}
在writeStreamHeader()方法中首先会往底层字节容器中写入表示序列化的Magic Number以及版本号,定义为
/**
* Magic number that is written to the stream header.
*/
final static short STREAM_MAGIC = (short)0xaced;
/**
* Version number that is written to the stream header.
*/
final static short STREAM_VERSION = 5;
接下来会调用writeObject()方法进行序列化,实现如下:
public final void writeObject(Object obj) throws IOException {
if (enableOverride) {
writeObjectOverride(obj);
return;
}
try {
// 调用writeObject0()方法序列化
writeObject0(obj, false);
} catch (IOException ex) {
if (depth == 0) {
writeFatalException(ex);
}
throw ex;
}
}
正常情况下会调用writeObject0()进行序列化操作,该方法实现如下:
private void writeObject0(Object obj, boolean unshared)
throws IOException
{
// 一些省略代码
try {
// 一些省略代码
Object orig = obj;
// 获取要序列化的对象的Class对象
Class cl = obj.getClass();
ObjectStreamClass desc;
for (;;) {
Class repCl;
// 创建描述cl的ObjectStreamClass对象
desc = ObjectStreamClass.lookup(cl, true);
// 其他省略代码
}
// 一些省略代码
// 根据实际的类型进行不同的写入操作
// remaining cases
if (obj instanceof String) {
writeString((String) obj, unshared);
} else if (cl.isArray()) {
writeArray(obj, desc, unshared);
} else if (obj instanceof Enum) {
writeEnum((Enum) obj, desc, unshared);
} else if (obj instanceof Serializable) {
// 被序列化对象实现了Serializable接口
writeOrdinaryObject(obj, desc, unshared);
} else {
if (extendedDebugInfo) {
throw new NotSerializableException(
cl.getName() + "" + debugInfoStack.toString());
} else {
throw new NotSerializableException(cl.getName());
}
}
} finally {
depth--;
bout.setBlockDataMode(oldMode);
}
}
从代码里面可以看到,程序会
这里可以解释一个问题:Serializbale接口是个空的接口,并没有定义任何方法,为什么需要序列化的接口只要实现Serializbale接口就能够进行序列化。
答案是:Serializable接口这是一个标识,告诉程序所有实现了”我”的对象都需要进行序列化。
因此,序列化过程接下来会执行到writeOrdinaryObject()这个方法中,该方法实现如下:
private void writeOrdinaryObject(Object obj,
ObjectStreamClass desc,
boolean unshared) throws IOException
{
if (extendedDebugInfo) {
debugInfoStack.push(
(depth == 1 ? "root " : "") + "object (class "" +
obj.getClass().getName() + "", " + obj.toString() + ")");
}
try {
desc.checkSerialize();
bout.writeByte(TC_OBJECT); // 写入Object标志位
writeClassDesc(desc, false); // 写入类元数据
handles.assign(unshared ? null : obj);
if (desc.isExternalizable() && !desc.isProxy()) {
writeExternalData((Externalizable) obj);
} else {
writeSerialData(obj, desc); // 写入被序列化的对象的实例数据
}
} finally {
if (extendedDebugInfo) {
debugInfoStack.pop();
}
}
}
在这个方法中首先会往底层字节容器中写入TC_OBJECT,表示这是一个新的Object
/**
* new Object.
*/
final static byte TC_OBJECT = (byte)0x73;
接下来会调用writeClassDesc()方法写入被序列化对象的类的类元数据,writeClassDesc()方法实现如下:
private void writeClassDesc(ObjectStreamClass desc, boolean unshared)
throws IOException
{
int handle;
if (desc == null) {
// 如果desc为null
writeNull();
} else if (!unshared && (handle = handles.lookup(desc)) != -1) {
writeHandle(handle);
} else if (desc.isProxy()) {
writeProxyDesc(desc, unshared);
} else {
writeNonProxyDesc(desc, unshared);
}
}
在这个方法中会先判断传入的desc是否为null,如果为null则调用writeNull()方法
private void writeNull() throws IOException {
// TC_NULL = (byte)0x70;
// 表示对一个Object引用的描述的结束
bout.writeByte(TC_NULL);
}
如果不为null,则一般情况下接下来会调用writeNonProxyDesc()方法,该方法实现如下:
private void writeNonProxyDesc(ObjectStreamClass desc, boolean unshared)
throws IOException