Java裡有一種物件叫java.io.Serializable
,是可以讓物件在Serialize後在不同的儲存體中傳遞。中文譯做序列化。 今天講講怎麼麼將物件存到硬碟這個儲存體…。
假設我有一個物件是這樣:他是一個Serializable
的物件。 裡面有一個Collection
(datas),可以用來存放Serializable
的物件。
public class FileDatas implements Serializable {
private static final long serialVersionUID = 8048736089512288707L;
public Collection<Serializable> datas;
public FileDatas() {
datas = new HashSet<Serializable>();
}
public Collection<Serializable> getDatas() {
return datas;
}
}
與另外一個Serializable物件Book
:
public class Book implements Serializable {
private static final long serialVersionUID = -4088035671812463272L;
private String isbn;
private String author;
private String name;
public Book() {
}
// Other gets and setters.
@Override
public String toString() {
return "Book [name=" + name + "]";
}
}
於是我要將Book
這個物件存為實體檔案與取得的方式,大概是這樣:
package taichitech.common.db;
import java.io.FileInputStream;
import java.io.FileOutputStream;
import java.io.Serializable;
import java.util.Collection;
import org.apache.commons.lang3.SerializationUtils;
import org.junit.Test;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
public class FileDatasTest {
Logger logger = LoggerFactory.getLogger(getClass());
@Test
public void testSetDatas() {
try (FileOutputStream fout = new FileOutputStream(filePath);) {
FileDatas fd = new FileDatas();
Collection<Serializable> datas = fd.getDatas();
datas.add(newExampleBook("994-443-989", "Tom Edsion", "How to Generate Java Class?"));
datas.add(newExampleBook("907-43-169", "Willion Smith", "Eclipse Pro, 2Ed"));
datas.add(newExampleBook("659-771-01", "Water 13", "如何銷售你自己"));
logger.debug("Books {}", datas);
SerializationUtils.serialize(fd, fout);
} catch (Exception e) {
logger.error("Fial", e);
}
}
private Book newExampleBook(String isbn, String author, String name) {
Book b = new Book();
b.setAuthor(author);
b.setIsbn(isbn);
b.setName(name);
return b;
}
private final String filePath = ".filedatas.ser";
@Test
public void testGetDatas() {
try (FileInputStream fin = new FileInputStream(filePath);) {
FileDatas fd = SerializationUtils.deserialize(fin);
logger.debug("Books {}", fd.getDatas());
} catch (Exception e) {
logger.error("Fial", e);
}
}
}
testGetDatas
示範了如何將物件存成檔案,而testGetDatas
示範如何將檔案再轉回物件。
這裡我主要是使用Apache commons-lang3的SerializationUtils
這個物件。 其實deserialize()
或serialize()
裡面就是將Object 轉成ObjectInputStream
或ObjectOutputStream
。
延申閱讀:
你可以參考如何轉Serializable物件轉成byte[]。
毫無疑問的,打算要存成檔案的物件,都必需要是Serialiazble,所以Collection裡的物件,或是相關property的型別,都必需要是Serializable。
2個UT測試的執行結果如下:
10:38:11.569 [main] DEBUG t.c.db.FileDatasTest[24]-Books [Book [name=Eclipse Pro, 2Ed], Book [name=How to Generate Java Class?], Book [name=如何銷售你自己]]
11:31:45.541 [main] DEBUG t.c.db.FileDatasTest[45]-Books [Book [name=How to Generate Java Class?], Book [name=如何銷售你自己], Book [name=Eclipse Pro, 2Ed]]
儲存的檔案,用文字篇輯器打開會是這個樣子:
這個檔案存了3個Book
物件與一個FileDatas
物件同場加印
我在unit test中產生Book
物件的方式就是Factory Method
的應用。
延申閱讀:
沒有留言 :
張貼留言