对象序列化

对象序列化的目标是将对象保存到磁盘中,或允许在网络中直接传输对象。对象序列化机制允许把内存中的 Java 对象转换成平台无关的二进制流,从而允许把这种二进制流持久地保存在磁盘上,通过网络将这种二进制流传输到另1个网络节点。其他程序一旦获得了这种二进制流(无论是从磁盘中获取的,还是通过网络获取的) ,都可以将这种二进制流恢复成原来的 Java 对象

如何来使用对象序列化?

前提:

首先,一个类要被序列化,那么它必须实现如下两个接口之一:
  • Serializable
  • Extemalizable
实现着两个接口的作用,其实就是就是标记一个对象是否可以被序列化。所以比如我们有一个类需要被序列化,我们实现Serializable接口就行,无需实现任何方法

序列化工具类:ObjectOutputStream

方法:

  • writeObject()

反序列化工具类:objectInputStream 

方法:

  • readObject()
示例:存储Person类对象
import java.io.*;

/**
* @ClassName ObjectOutputStreamWriteObjectExample
* @projectName: object1
* @author: Zhangmingda
* @description: Person 类实现序列化接口
* date: 2021/4/18.
*/
public class ObjectOutputStreamWriteObjectExample {
//实现接口Serializable可以序列化
private static class Person implements Serializable {
String name;
int age; public Person(String name, int age) {
this.name = name;
this.age = age;
}
@Override
public String toString() {
return "Person{" +
"name='" + name + '\'' +
", age=" + age +
'}';
}
}
//序列化方法
private static void writeObject(Person person,String dstPath) {
try(ObjectOutputStream objectOutputStream = new ObjectOutputStream(new FileOutputStream(dstPath))){
objectOutputStream.writeObject(person);
} catch (IOException e) {
e.printStackTrace();
}
}
//反序列化方法
private static<T> void readObject(String srcPath){
try(ObjectInputStream objectInputStream = new ObjectInputStream(new FileInputStream(srcPath))){
T person = (T) objectInputStream.readObject();
System.out.println(person.getClass());
System.out.println(person);
/**
* class ObjectOutputStreamWriteObjectExample$Person
* Person{name='钱老大', age=30}
*/
} catch (IOException e) {
e.printStackTrace();
} catch (ClassNotFoundException e) {
e.printStackTrace();
}
}
public static void main(String[] args) {
Person person = new Person("钱老大",30);
String dstPath = "输入输出文件读写/src/test/output/object-save.txt";
writeObject(person,dstPath);
String srcPath = "输入输出文件读写/src/test/output/object-save.txt";
readObject(srcPath);
}
}
示例:带有引用变量的对象序列化
引用类型也必须是可以序列化的。
import java.io.*;

/**
* @ClassName ObjectOutputStreamWriteObjectExample
* @projectName: object1
* @author: Zhangmingda
* @description: Person 类实现序列化接口
* date: 2021/4/18.
*/
public class ObjectOutputStreamWriteObjectExample {
//实现接口Serializable可以序列化
private static class Person implements Serializable {
String name;
int age;
Job job; public Person(String name, int age, Job job) {
this.name = name;
this.age = age;
this.job = job;
} public Person(String name, int age) {
this.name = name;
this.age = age;
} @Override
public String toString() {
return "Person{" +
"name='" + name + '\'' +
", age=" + age +
", job=" + job.getName() +
'}';
}
}
private static class Job implements Serializable {
private String name; public Job(String name) {
this.name = name;
}
public String getName() {
return name;
}
} //序列化方法
private static void writeObject(Person person,String dstPath) {
try(ObjectOutputStream objectOutputStream = new ObjectOutputStream(new FileOutputStream(dstPath))){
objectOutputStream.writeObject(person);
} catch (IOException e) {
e.printStackTrace();
}
}
//反序列化方法
private static<T> void readObject(String srcPath){
try(ObjectInputStream objectInputStream = new ObjectInputStream(new FileInputStream(srcPath))){
T person = (T) objectInputStream.readObject();
System.out.println(person.getClass());
System.out.println(person);
/**
* class ObjectOutputStreamWriteObjectExample$Person
* Person{name='钱老大', age=30, job=教师}
*/
} catch (IOException e) {
e.printStackTrace();
} catch (ClassNotFoundException e) {
e.printStackTrace();
}
}
public static void main(String[] args) {
Person person = new Person("钱老大",30,new Job("教师"));
String dstPath = "输入输出文件读写/src/test/output/object-save.txt";
writeObject(person,dstPath);
String srcPath = "输入输出文件读写/src/test/output/object-save.txt";
readObject(srcPath);
}
}

指定哪些字段不需要序列化

比如上面的Person对象,可能有的女生认为年龄是一个秘密,不应该被序列化,怎么办?
transient关键字修饰对应的字段就OK了
示例:private transient int age;

存入:Person{name='钱老大', age=30, job=教师}

读取:Person{name='钱老大', age=0, job=教师} 【不被反序列化的字段置为 对应数据类型默认值

//序列化写入到文件时transient 未设置,读取时添加了transient,等于对象的类在写入后,读取之前又发生了变化,然后反序列化读取发生
错误类似:local class incompatible: stream classdesc serialVersionUID ......

解决:类在创建时 添加serialVersionUID字段来保证类发生变化后,也能反序列化成功(不被反序列化的字段置为 对应数据类型默认值)

即:类的升级

import java.io.*;

/**
* @ClassName ObjectOutputStreamWriteObjectExample
* @projectName: object1
* @author: Zhangmingda
* @description: Person 类实现序列化接口
* date: 2021/4/18.
*/
public class ObjectOutputStreamWriteObjectExample {
//实现接口Serializable可以序列化
private static class Person implements Serializable {
private static final long serialVersionUID = 769204331117184540L;
private String name;
private transient int age;
private Job job; public Person(String name, int age, Job job) {
this.name = name;
this.age = age;
this.job = job;
} public Person(String name, int age) {
this.name = name;
this.age = age;
} @Override
public String toString() {
return "Person{" +
"name='" + name + '\'' +
", age=" + age +
", job=" + job.getName() +
'}';
}
}
private static class Job implements Serializable {
private String name; public Job(String name) {
this.name = name;
}
public String getName() {
return name;
}
} //序列化方法
private static void writeObject(Person person,String dstPath) {
try(ObjectOutputStream objectOutputStream = new ObjectOutputStream(new FileOutputStream(dstPath))){
objectOutputStream.writeObject(person);
} catch (IOException e) {
e.printStackTrace();
}
}
//反序列化方法
private static<T> void readObject(String srcPath){
try(ObjectInputStream objectInputStream = new ObjectInputStream(new FileInputStream(srcPath))){
T person = (T) objectInputStream.readObject();
System.out.println(person.getClass());
System.out.println(person);
/**
* class ObjectOutputStreamWriteObjectExample$Person
* Person{name='钱老大', age=30, job=教师}
*/
} catch (IOException e) {
e.printStackTrace();
} catch (ClassNotFoundException e) {
e.printStackTrace();
}
}
public static void main(String[] args) {
// Person person = new Person("钱老大",30,new Job("教师"));
// String dstPath = "输入输出文件读写/src/test/output/object-save.txt";
// writeObject(person,dstPath);
String srcPath = "输入输出文件读写/src/test/output/object-save.txt";
readObject(srcPath);
}
}
 
 
 
 
 
 
 

java 输入输出 对象序列化implements Serializable与反序列化:ObjectOutputStream.writeObject() ;objectInputStream.readObject() ;serialVersionUID字段注意的更多相关文章

  1. Java Io 对象序列化和反序列化

    Java 支持将任何对象进行序列化操作,序列化后的对象文件便可通过流进行网络传输. 1.      对象序列化就是将对象转换成字节序列,反之叫对象的反序列化 2.      序列化流ObjectOut ...

  2. 【java】对象序列化Serializable、transient

    package 对象序列化; import java.io.Serializable; @SuppressWarnings("serial") class A implements ...

  3. Java之对象序列化和反序列化

    一.对象序列化和反序列化存在的意义: 当你创建对象,只要你需要,他就一直存在,但当程序结束,对象就会消失,但是存在某种情况,如何让程序在不允许的状态,仍然保持该对象的信息.并在下次程序运行的时候使用该 ...

  4. Java程序设计——对象序列化

    对象序列化的目标是将对象保存到磁盘中或允许在网络中直接传输对象,对象序列化机制允许把内存中的Java对象转换成平台无关的二进制流,从而允许把这种二进制流持久保存在磁盘上,通过网络将这种二进制流传输到另 ...

  5. 谈谈 JAVA 的对象序列化

    所谓的『JAVA 对象序列化』就是指,将一个 JAVA 对象所描述的所有内容以文件 IO 的方式写入二进制文件的一个过程.关于序列化,主要涉及两个流,ObjectInputStream 和 Objec ...

  6. java对象序列化byte[] and byte[]反序列化对象--转

    import java.io.ByteArrayInputStream; import java.io.ByteArrayOutputStream; import java.io.IOExceptio ...

  7. js对象序列化JSON.stringify()与反序列化JSON.parse()

    草稿: parse用于从一个字符串中解析出json对象,如 var str = '{"name":"huangxiaojian","age" ...

  8. JAVA基础之——序列化和反序列化

    1 概念 序列化,将java对象转换成字节序列的过程. 反序列化,将字节序列恢复成java对象的过程. 2 为什么要序列化? 2.1 实现数据持久化,当对象创建后,它就会一直在,但是在程序终止时,这个 ...

  9. Java 序列化 对象序列化和反序列化

    Java 序列化 对象序列化和反序列化 @author ixenos 对象序列化是什么 1.对象序列化就是把一个对象的状态转化成一个字节流. 我们可以把这样的字节流存储为一个文件,作为对这个对象的复制 ...

随机推荐

  1. SQL 跨实例操作

    SQL 跨实例操作 我使用的是 OpenDataSource 函数,假设你要在其他机器上访问 192.168.0.1 上的数据库: SELECT A.[Name], B.[SkillName], B. ...

  2. [Noip 2018][标题统计 龙湖斗 摆渡车 对称二叉树]普及组题解

    啊喂,都已经9102年了,你还在想去年? 这里是一个Noip2018年PJ第二题打爆的OIer,错失省一 但经过了一年,我学到了很多,也有了很多朋友,水平也提高了很多,现在回看当时: 今年的Noip ...

  3. SAM 做题笔记(各种技巧,持续更新,SA)

    SAM 感性瞎扯. 这里是 SAM 做题笔记. 本来是在一篇随笔里面,然后 Latex 太多加载不过来就分成了两篇. 标 * 的是推荐一做的题目. trick 是我总结的技巧. I. P3804 [模 ...

  4. Vue 中 $on $once $off $emit 详细分析,以及使用

    vue的 $on,$emit,$off,$once Api 中的解释: $on(eventName:string|Array, callback) 监听事件 监听当前实例上的自定义事件.事件可以由 v ...

  5. 监听浏览器tab切换

    监听浏览器切屏 为了完成验证用户在切换浏览器tab时进行登录再次认证需求需要监听浏览器切换窗口 if (document.hidden !== undefined) { document.addEve ...

  6. R语言hist重叠图作法

    set.seed(1) h1<-hist(rnorm(1000,100,5)) h2<-hist(rnorm(1000,99,5)) plot(h2,col=rgb(255,0,0,50, ...

  7. Python基础之格式化输出的三种方式

    目录 1. 格式化输出的三种方式 1.1 占位符 1.2 format格式化 1.3 f-string格式化 1. 格式化输出的三种方式 在程序中,需要将输出信息打印成固定的格式,这时候就需要格式化输 ...

  8. 宏GENERATED_BODY做了什么?

    Version:4.26.2 UE4 C++工程名:MyProject \ 一般语境下,我们说c++源码的编译大体分为:预处理.编译.链接; cppreference-translation_phas ...

  9. Python中的随机采样和概率分布(二)

    在上一篇博文<Python中的随机采样和概率分布(一)>(链接:https://www.cnblogs.com/orion-orion/p/15647408.html)中,我们介绍了Pyt ...

  10. A Child's History of England.37

    Many other noblemen repeating and supporting this when it was once uttered, Stephen and young Planta ...