Java Serializable

时间:2009-08-07 11:14:39

标签: java serialization

我已经制作了一个序列化的类,就像这样

`

class Example implements Serializable
{
    transient byte i=2;
    transient byte j=3;
    Example(){System.out.println("value of i:"+i+",j:"+j);}
}

`
当我对该类进行反序列化时,即

    class SerialClass
{
public static void main(String []r)//throws IOException
{
try{
    System.out.println("Serialization");
    Example e=new Example();
    FileOutputStream out=new FileOutputStream("hyxa_code.txt");
/*File f=new File("copt.txt");
f.createNewFile();*/
    ObjectOutputStream oo=new ObjectOutputStream(out);
    oo.writeObject(e);
    oo.close();}catch(IOException e){}


try{
System.out.println("Deserialization");
    Example ee=new Example();
FileInputStream in=new FileInputStream("hyxa_code.txt");
ObjectInputStream o=new ObjectInputStream(in);
ee=(Example)o.readObject();
System.out.println("The vlaue of i,j:"+ee.i+" "+ee.j);
}catch(IOException e)
{}
catch(ClassNotFoundException e){}
}
}

输出是这样的:

Serialization
value of i:2,j:3
Deserialization
value of i:2,j:3
The vlaue of i,j:0 0

但正如我所听到的,反序列化不会初始化构造函数, 这里正在发生,为什么??? 另外,为什么两个变量的值都在初始化时出现

4 个答案:

答案 0 :(得分:4)

将变量标记为瞬态会使它们不被序列化。删除变量声明的瞬态部分,它将起作用。

对于未在反序列化过程中调用的构造函数,您是正确的。对象的状态直接从流加载,不调用构造函数。

有关详细信息,请参阅http://www.rockstarprogrammer.org/post/2006/jul/29/more_you_want_know_about_java_serialization/。当反序列化发生时,readObject方法可用于初始化瞬态变量。

答案 1 :(得分:4)

您显式调用构造函数两次 - 一次序列化,然后在反序列化时调用一次:

Example ee=new Example();
FileInputStream in=new FileInputStream("hyxa_code.txt");
ObjectInputStream o=new ObjectInputStream(in);
ee=(Example)o.readObject();
System.out.println("The vlaue of i,j:"+ee.i+" "+ee.j);

你忽略了你创造的价值,所以代码实际上是这样的:

FileInputStream in=new FileInputStream("hyxa_code.txt");
ObjectInputStream o=new ObjectInputStream(in);
Example ee=(Example)o.readObject();
System.out.println("The vlaue of i,j:"+ee.i+" "+ee.j);

不同之处在于,这次你不会不必要地调用构造函数。

这就解释了为什么你会两次看到“i:2,j:3”的值。反序列化对象的值为0的原因是因为您已将变量声明为transient,如其他答案中所述。

答案 2 :(得分:2)

瞬态变量不能被序列化,因此变量的值变为0。

这里有一个例子:http://javatechnologyhelper.blogspot.com/2014/04/java-serialization.html

另外,您可以查看:http://en.wikibooks.org/wiki/Java_Programming/Keywords/transient

  

transient是一个Java关键字,它标记成员变量不是   在持久化为字节流时序列化。当一个物体是   通过网络传输,该对象需要被序列化'。   序列化将对象状态转换为串行字节。那些字节   通过网络发送,并从那些重新创建对象   字节。由java transient关键字标记的成员变量不是   转移,他们故意丢失。

答案 3 :(得分:1)

由于i和j都被标记为瞬态,因此它们不会被序列化。因此,当您反序列化时,它们将具有byte的默认值,即0。