title: 序列化
date: 2021-06-07 22:42:01
tags: 序列化
categories: Java
description:
top_img:
comments:
cover:
序列化
序列化和反序列化是什么
当两个进程远程通信时,彼此可以发送各种类型的数据。 无论是何种类型的数据,都会以二进制序列的形式在网络上传送。比如,我们可以通过http协议发送字符串信息;我们也可以在网络上直接发送Java对象。发送方需要把这个Java对象转换为字节序列,才能在网络上传送;接收方则需要把字节序列再恢复为Java对象才能正常读取。
把Java对象转换为字节序列的过程称为对象的序列化。把字节序列恢复为Java对象的过程称为对象的反序列化。
对象序列化的作用有如下两种:
-
持久化: 把对象的字节序列永久地保存到硬盘上,通常存放在一个文件中,比如:休眠的实现。以后服务器session管理,hibernate将对象持久化实现。
-
网络通信:在网络上传送对象的字节序列。比如:服务器之间的数据通信、对象传递。
序列化涉及的类和接口
ObjectOutputStream 代表对象输出流,它的 writeObject(Object obj) 方法可对参数指定的obj对象进行序列化,把得到的字节序列写到一个目标输出流中。
ObjectInputStream 代表对象输入流,它的 readObject() 方法从一个源输入流中读取字节序列,再把它们反序列化为一个对象,并将其返回。
只有实现了Serializable接口的类的对象才能被序列化。 Serializable接口是一个空接口,只起到标记作用。
class Person implements Serializable {
// 添加序列化ID,它决定着是否能够成功反序列化!
private static final long serialVersionUID = 1L;
int age;
boolean isMan;
String name;
public Person(int age, boolean isMan, String name) {
super();
this.age = age;
this.isMan = isMan;
this.name = name;
}
}
public class TestSerializable {
public static void main(String[] args) {
FileOutputStream fos = null;
ObjectOutputStream oos = null;
ObjectInputStream ois = null;
FileInputStream fis = null;
try {
// 通过ObjectOutputStream将Person对象的数据写入到文件中,即序列化。
Person person = new Person(18, true, "高淇");
// 序列化
fos = new FileOutputStream("d:/c.txt");
oos = new ObjectOutputStream(fos);
oos.writeObject(person);
oos.flush();
// 反序列化
fis = new FileInputStream("d:/c.txt");
// 通过ObjectInputStream将文件中二进制数据反序列化成Person对象:
ois = new ObjectInputStream(fis);
Person p = (Person) ois.readObject();
System.out.println(p);
} catch (ClassNotFoundException e) {
e.printStackTrace();
} catch (IOException e) {
e.printStackTrace();
} finally {
if (oos != null) {
try {
oos.close();
} catch (IOException e) {
e.printStackTrace();
}
}
if (fos != null) {
try {
fos.close();
} catch (IOException e) {
e.printStackTrace();
}
}
if (ois != null) {
try {
ois.close();
} catch (IOException e) {
e.printStackTrace();
}
}
if (fis != null) {
try {
fis.close();
} catch (IOException e) {
e.printStackTrace();
}
}
}
}
}
Apache IOUtils和FileUtils的使用
FieUtils类中常用方法的介绍
cleanDirectory:清空目录,但不删除目录。
contentEquals:比较两个文件的内容是否相同。
copyDirectory:将一个目录内容拷贝到另一个目录。可以通过FileFilter过滤需要拷贝的 文件。
copyFile:将一个文件拷贝到一个新的地址。
copyFileToDirectory:将一个文件拷贝到某个目录下。
copyInputStreamToFile:将一个输入流中的内容拷贝到某个文件。
deleteDirectory:删除目录。
deleteQuietly:删除文件。
listFiles:列出指定目录下的所有文件。
openInputSteam:打开指定文件的输入流。
readFileToString:将文件内容作为字符串返回。
readLines:将文件内容按行返回到一个字符串数组中。
size:返回文件或目录的大小。
write:将字符串内容直接写到文件中。
writeByteArrayToFile:将字节数组内容写到文件中。
writeLines:将容器中的元素的toString方法返回的内容依次写入文件中。
writeStringToFile:将字符串内容写到文件中。
import java.io.File;
import java.io.FileFilter;
import org.apache.commons.io.FileUtils;
public class TestUtils2 {
public static void main(String[] args) throws Exception {
FileUtils.copyDirectory(new File("d:/aaa"), new File("d:/bbb"), new FileFilter() {
@Override
public boolean accept(File pathname) {
// 使用FileFilter过滤目录和以html结尾的文件
if (pathname.isDirectory() || pathname.getName().endsWith("html")) {
return true;
} else {
return false;
}
}
});
}
}
IOUtils的妙用
buffer方法:将传入的流进行包装,变成缓冲流。并可以通过参数指定缓冲大小。
closeQueitly方法:关闭流。
contentEquals方法:比较两个流中的内容是否一致。
copy方法:将输入流中的内容拷贝到输出流中,并可以指定字符编码。
copyLarge方法:将输入流中的内容拷贝到输出流中,适合大于2G内容的拷贝。
lineIterator方法:返回可以迭代每一行内容的迭代器。
read方法:将输入流中的部分内容读入到字节数组中。
readFully方法:将输入流中的所有内容读入到字节数组中。
readLine方法:读入输入流内容中的一行。
toBufferedInputStream,toBufferedReader:将输入转为带缓存的输入流。
toByteArray,toCharArray:将输入流的内容转为字节数组、字符数组。
toString:将输入流或数组中的内容转化为字符串。
write方法:向流里面写入内容。
writeLine方法:向流里面写入一行内容。
import java.io.*;
import org.apache.commons.io.IOUtils;
public class TestUtils3 {
public static void main(String[] args) throws Exception {
String content = IOUtils.toString(new FileInputStream("d:/a.txt"),"gbk");
System.out.println(content);
}
}
© 著作权归作者所有
相关热门文章
发表评论