If you have ever implemented Serializable interface, you must encounter this warning message

The serializable class xxx does not declare a static final serialVersionUID field of type long

So…what is serialVersionUID?

The serialVersionUID is used as a version control in a Serializable class. If you do not explicitly declare a serialVersionUID, JVM will do it for you automatically, based on various aspects of your Serializable class, as described in the Java(TM) Object Serialization Specification.

1. SerialVersionUID Example

The above statement is a bit hard to understand at the beginning (at least I did), let start an example to understand how Serializable class use SerialVersionUID to implement version control.

1.1 Address.java

A serializable class with a serialVersionUID of 1L.

import java.io.Serializable;

public class Address implements Serializable{

	   private static final long serialVersionUID = 1L;

	   String street;
String country; public void setStreet(String street){
this.street = street;
} public void setCountry(String country){
this.country = country;
} public String getStreet(){
return this.street;
} public String getCountry(){
return this.country;
} @Override
public String toString() {
return new StringBuffer(" Street : ")
.append(this.street)
.append(" Country : ")
.append(this.country).toString();
}
}

1.2 WriteObject.java

A simple class to write / serialize the Address object into a file – “c:\\address.ser”.

import java.io.FileOutputStream;
import java.io.ObjectOutputStream; public class WriteObject{ public static void main (String args[]) { Address address = new Address();
address.setStreet("wall street");
address.setCountry("united states"); try{ FileOutputStream fout = new FileOutputStream("c:\\address.ser");
ObjectOutputStream oos = new ObjectOutputStream(fout);
oos.writeObject(address);
oos.close();
System.out.println("Done"); }catch(Exception ex){
ex.printStackTrace();
}
}
}

1.3 ReadObject.java

A simple class to read / deserialize the Address object from file – “c:\\address.ser”.

import java.io.FileInputStream;
import java.io.ObjectInputStream; public class ReadObject{ public static void main (String args[]) { Address address; try{ FileInputStream fin = new FileInputStream("c:\\address.ser");
ObjectInputStream ois = new ObjectInputStream(fin);
address = (Address) ois.readObject();
ois.close(); System.out.println(address); }catch(Exception ex){
ex.printStackTrace();
}
}
}

2. Testing

Let do some testing to demonstrate the use of serialVersionUID.

2.1 Same serialVersionUID

Same serialVersionUID , there is no problem during the deserialization process

javac Address.java
javac WriteObject.java
javac ReadObject.java
java WriteObject
java ReadObject
Street : wall street Country : united states

2.2 Different serialVersionUID

In Address.java, change the serialVersionUID to 2L (it was 1L), and compile it again.

javac Address.java
java ReadObject
java.io.InvalidClassException: Address; local class incompatible:
stream classdesc serialVersionUID = 1, local class serialVersionUID = 2
...
at ReadObject.main(ReadObject.java:14)

The “InvalidClassException” will raise, because you write a serialization class with serialVersionUID “1L” but try to retrieve it back with updated serialization class, serialVersionUID “2L”.

The serialVersionUID have to match during the serialization and deserialization process.

When should update your serialVersionUID? When your serialization class is updated with some incompatible Java type changes to a serializable class, you have to update your serialVersionUID.

For detail about the compatible and incompatible Java type changes to a serializable class, see the Java Object Serialization Specification.

3. What’s wrong with the default serialVersionUID?

If no serialVersionUID is declared, JVM will use its own algorithm to generate a default SerialVersionUID, you can check the algorithm here.

The default serialVersionUID computation is highly sensitive to class details and may vary from different JVM implementation, and result in an unexpected InvalidClassExceptions during the deserialization process.

3.1 Client / Server environment

– Client is using SUN’s JVM in Windows. – Server is using JRockit in Linux.

The client sends a serializable class with default generated serialVersionUID (e.g 123L) to the server over socket, the server may generate a different serialVersionUID (e.g 124L) during deserialization process, and raises an unexpected InvalidClassExceptions.

3.2 File / Database environment

– App #1 is using SUN’s JVM in Windows. – App #2 is using JRockit in Linux.

Serialization has allowed to save into a file or database. App #1 stores a serializable class into database by default generated serialVersionUID (e.g 123L), while App #2 may generate a different serialVersionUID (e.g 124L) during deserialization process, and raise an unexpected InvalidClassExceptions.

You can check here for the List of the JVM implementation.

4. How to generate serialVersionUID

You can use JDK “serialver” or Eclipse IDE to generate serialVersionUID automatically, see detail.

Conclusion

SUN is highly recommended developers to declare the serialVersionUID in order to avoid the different JVM issue listed above, however I rather recommend you should understand what is serialization, how serialVersionUID implement version control and why your class need to use serialization. Understand the serialVersionUID concept is better than blindfold to any recommendation.

References

  1. http://en.wikipedia.org/wiki/List_of_JVM_implementations
  2. http://java.sun.com/javase/6/docs/platform/serialization/spec/class.html#4100
  3. http://stackoverflow.com/questions/419796/explicit-serialversionuid-considered-harmful
  4. http://en.wikipedia.org/wiki/Serialization#Java
  5. http://www.javaworld.com/javaworld/jw-02-2006/jw-0227-control.html?page=1
  6. http://www.javablogging.com/what-is-serialversionuid/
  7. http://java.dzone.com/articles/dont-ignore-serialversionuid
  8. http://www.java-forums.org/new-java/8196-serialversionuid.html

【转载】 http://www.mkyong.com/java-best-practices/understand-the-serialversionuid/

【转载】Understand the serialVersionUID的更多相关文章

  1. local class incompatible: stream classdesc serialVersionUID = -2897844985684768944, local class serialVersionUID = 7350468743759137184

    local class incompatible: stream classdesc serialVersionUID = 1, local class serialVersionUID = 2427 ...

  2. Java中serialVersionUID的解释及两种生成方式的区别(转载)

    转载自:http://blog.csdn.net/xuanxiaochuan/article/details/25052057 serialVersionUID作用:        序列化时为了保持版 ...

  3. 转载:AbstractQueuedSynchronizer的介绍和原理分析

    简介 提供了一个基于FIFO队列,可以用于构建锁或者其他相关同步装置的基础框架.该同步器(以下简称同步器)利用了一个int来表示状态,期望它能够成为实现大部分同步需求的基础.使用的方法是继承,子类通过 ...

  4. JAVA中SERIALVERSIONUID的解释

    serialVersionUID作用:        序列化时为了保持版本的兼容性,即在版本升级时反序列化仍保持对象的唯一性.有两种生成方式:       一个是默认的1L,比如:private st ...

  5. [转载] Java高新技术第一篇:类加载器详解

    本文转载自: http://blog.csdn.net/jiangwei0910410003/article/details/17733153 首先来了解一下字节码和class文件的区别: 我们知道, ...

  6. 【转载】Recommendations with Thompson Sampling (Part II)

    [原文链接:http://engineering.richrelevance.com/recommendations-thompson-sampling/.] [本文链接:http://www.cnb ...

  7. 【转载】安卓APP架构

    注:本篇博文转载于 http://my.oschina.net/mengshuai/blog/541314?fromerr=z8tDxWUH 本文介绍了文章作者从事了几年android应用的开发,经历 ...

  8. JavaWeb防止表单重复提交(转载)

    转载自:http://blog.csdn.net/ye1992/article/details/42873219 在平时开发中,如果网速比较慢的情况下,用户提交表单后,发现服务器半天都没有响应,那么用 ...

  9. Java序列化中的SerialVersionUid

    版权声明:本文为博主fbysss原创文章,转载请注明出处 作者:fbysssmsn:jameslastchina@hotmail.com  blog:blog.csdn.NET/fbysss声明:本文 ...

随机推荐

  1. ionic中的service简单写法

    在service中写服务 服务名叫feedService .service('feedService',function($ionicLoading,$q,$http){ return{ //获取反馈 ...

  2. myeclipse10中文注释乱码问题

    将别人的项目或JAVA文件导入到自己的Eclipse中时,常常会出现JAVA文件的中文注释变成乱码的情况,主要原因就是别人的IDE编码格式和自己的Eclipse编码格式不同. 总结网上的建议和自己的体 ...

  3. python3 filter用法(举例求0~n之间的素数)

    在用python3求0~n之间的素数时,关于filter用法的有点模糊,于是上网查了一下filter用法. 求0~n之间素数的脚本prime.py: def f(x): plist = [0,0] + ...

  4. 初识Java-分数录入系统

    package classTest; import java.util.Scanner; public class scoreArrangement { /**  * 选择界面(main)  */ p ...

  5. Scrolliview

    package com.example.scrollview; import android.os.Bundle;import android.app.Activity;import android. ...

  6. Ruby 方法

    Ruby 方法 Ruby 方法与其他编程语言中的函数类似.Ruby 方法用于捆绑一个或多个重复的语句到一个单元中. 方法名应以小写字母开头.如果您以大写字母作为方法名的开头,Ruby 可能会把它当作常 ...

  7. 【转载】ANSYS完全法与模态叠加法瞬态分析实例

    原文地址:http://www.caetecc.com/thread-2172-1-1.html ! 半脉冲载荷 --- 模态叠加法fini/clear,nostart/PREP7ET,1,BEAM4 ...

  8. [leetcode] 根据String数组构造TreeNode,用于LeetCode树结构相关的测试用例

    LeetCode 跟树结构相关的题目的测试用例中大多是通过String数组来构造树.例如{2,#,3,#,4,#,5,#,6},可以构造出如下的树(将树结构逆时针选择90度显示): 6         ...

  9. 用Windows PowerShell 控制管理 Microsoft Office 365

    如果想要通过PowerShell控制管理Office365,首先要安装Microsoft Online Services Sign-In Assistant 7.0,链接如下 Microsoft On ...

  10. (转)The Neural Network Zoo

    转自:http://www.asimovinstitute.org/neural-network-zoo/ THE NEURAL NETWORK ZOO POSTED ON SEPTEMBER 14, ...