参考博客:
“Java的serialization提供了一种持久化对象实例的机制。当持久化对象时,可能有一个特殊的对象数据成员,我们不想用serialization机制来保存它。为了在一个特定对象的一个域上关闭serialization,可以在这个域前加上关键字transient。transient是Java语言的关键字,用来表示一个域不是该对象串行化的一部分。当一个对象被串行化的时候,transient型变量的值不包括在串行化的表示中,然而非transient型的变量是被包括进去的。”
为了验证这个问题,我们写代码:设置一个普通属性,一个transient标记的属性,然后将对象串行化后再读出来,发现transient标记的属性并没有被串行化。
1 public class MyTransient implements java.io.Serializable { 2 /** 3 * 4 */ 5 private static final long serialVersionUID = -8771981914596808776L; 6 private Date loggingDate = new Date(); 7 private String uid; 8 private transient String pwd; 9 10 public MyTransient(String user, String password) {11 uid = user;12 pwd = password;13 }14 15 public String toString() {16 String password = null;17 if (pwd == null) {18 password = "NOT SET";19 } else {20 password = pwd;21 }22 return "logon info: \n " + "user: " + uid + "\n logging date : " + loggingDate.toString()23 + "\n password: " + password;24 }25 26 public static void main(String[] args) {27 MyTransient logInfo = new MyTransient("MIKE", "MECHANICS");28 System.out.println(logInfo.toString());29 try {30 ObjectOutputStream o = new ObjectOutputStream(new FileOutputStream("logInfo.out"));31 o.writeObject(logInfo);32 o.close();33 ObjectInputStream in = new ObjectInputStream(new FileInputStream("logInfo.out"));34 MyTransient logInfo1 = (MyTransient) in.readObject();35 System.out.println(logInfo1.toString());36 } catch (Exception e) {37 }38 }
文末作者提醒:粗心对待transient域可能引起的潜在问题。
1 public class GuestLoggingInfo implements java.io.Serializable { 2 private Date loggingDate = new Date(); 3 private String uid; 4 private transient String pwd; 5 6 GuestLoggingInfo() { 7 uid = "guest"; 8 pwd = "guest"; 9 }10 11 public String toString() {12 // same as above13 }14 }
现在,如果我们穿行化GuestLoggingInfo的一个实例,将它写入磁盘,并且再将它从磁盘中读出,我们仍然看到读回的对象打印password 为 "NOT SET"。当从磁盘中读出某个类的实例时,实际上并不会执行这个类的构造函数,而是载入了一个该类对象的持久化状态,并将这个状态赋值给该类的另一个对象。
http://www.blogjava.net/fhtdy2004/archive/2009/06/20/286112.html