用java原生介面Serializable實現對單例物件的序列化
阿新 • • 發佈:2018-12-30
單例類,也是將要序列化的類
package test;
import java.io.Serializable;
import java.util.Date;
/**
* 定義一個可序列化的單例類,單例實現方法是靜態內部類實現 同時為了在序列化後,再次反序列化獲得物件還是單例模式。用readResolve方法
* 對於這個不是很懂。
*
* @author cindy
*
*/
public class MyObject implements Serializable {
/**
* 序列碼
*/
private static final long serialVersionUID = 8881L;
private String name = "";
private Date birthday = null;
private String address = "";
public String getName() {
return name;
}
public void setName(String name) {
this.name = name;
}
public Date getBirthday() {
return birthday;
}
public void setBirthday(Date birthday) {
this.birthday = birthday;
}
public String getAddress() {
return address;
}
public void setAddress(String address) {
this.address = address;
}
public static long getSerialversionuid() {
return serialVersionUID;
}
private MyObject() {
// TODO Auto-generated constructor stub
}
// 內部類實現單例模式
private static class MyObjectHandler {
private static final MyObject myobject = new MyObject();
}
public static MyObject getInstance() {
return MyObjectHandler.myobject;
}
protected Object readResolve() {
System.out.println("呼叫了readResolve方法");
return MyObjectHandler.myobject;
}
}
檔案服務類
序列化是將資料持久化存到檔案中的
package file.service;
import java.io.File;
import java.io.IOException;
import test.run.SerialAndUnserial;
public class FileService {
public FileService() {
// TODO Auto-generated constructor stub
}
public static File createAndOpenFile(String filepath) {
if (filepath == null || filepath == "") {
return null;
}
String basePath = SerialAndUnserial.class.getResource("/").getFile();
// 這裡你可以看到classpath的地址在哪裡
System.out.println("classpath路徑" + basePath);
File file = null;
/**
* 有getCanonicalFile的效果是將含有的跳轉到上層目錄的../去掉。構成一個可以解析的目錄
* 形成這種形式/home/cindy/eclipseworkspace/singleton_serial/txt/object. txt
* 在沒有getCanonicalFile()方法呼叫前是這樣的。
* /home/cindy/eclipseworkspace/singleton_serial/../txt/object.txt
* 你可以把那個方法去掉試下。貌似去掉也可以正常執行。
*/
try {
file = new File(basePath, filepath).getCanonicalFile();
} catch (IOException e2) {
// TODO Auto-generated catch block
e2.printStackTrace();
}
System.out.println("該路徑的父級目錄" + file.getParent());
// 判定這個抽象路徑名錶示的路徑是否存在
System.out.println(file.exists());
if (!file.exists()) {
// 將所有缺少父級目錄都建立好
file.getParentFile().mkdirs();
try {// 最後建立檔案
file.createNewFile();
return file;
} catch (IOException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
}
System.out.println(file.exists());
return file;
}
}
測試用例
package test.run;
import java.io.File;
import java.io.FileInputStream;
import java.io.FileOutputStream;
import java.io.ObjectInputStream;
import java.io.ObjectOutputStream;
import java.util.Date;
import file.service.FileService;
import test.MyObject;
public class SerialAndUnserial {
public SerialAndUnserial() {
// TODO Auto-generated constructor stub
}
@SuppressWarnings("deprecation")
public static void main(String[] args) {
MyObject myObject = MyObject.getInstance();
myObject.setAddress("廣州市番禺區廣東工業大學");
myObject.setBirthday(new Date(2012, 0, 21));
myObject.setName("vincent");
String relativePath = "../txt/object.txt";
// System.out.println(SerialAndUnserial.class.getResource("/").getFile());
// System.out.println(SerialAndUnserial.class.getClassLoader().getResource("/").getFile());
File file = FileService.createAndOpenFile(relativePath);
System.out.println(file.getPath());
try {
FileOutputStream fos = new FileOutputStream(file);
ObjectOutputStream oos = new ObjectOutputStream(fos);
oos.writeObject(myObject);
oos.close();
fos.close();
System.out.println("MyObject例項序列化前的雜湊值" + myObject.hashCode());
System.out.println(myObject.getAddress() + "\t" + myObject.getName() + "\t" + myObject.getBirthday());
} catch (Exception e) {
// TODO Auto-generated catch block
e.printStackTrace();
} finally {
}
try {
FileInputStream fis = new FileInputStream(file);
ObjectInputStream objectInputStream = new ObjectInputStream(fis);
MyObject mObject = (MyObject) objectInputStream.readObject();
objectInputStream.close();
fis.close();
System.out.println("MyObject例項序列化後的雜湊值" + mObject.hashCode());
System.out.println(mObject.getAddress() + "\t" + mObject.getName() + "\t" + mObject.getBirthday());
} catch (Exception e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
}
}
最後呈現的結果