网站首页 > java教程 正文
首先,在Java开发中之所以需要序列化,核心目的是为了解决网络通信之间的对象传输问题。也就是说,如何把当前JVM进程里面的一个对象,跨网络传输到另一个JVM进程里面。
序列化,就是把内存里面的对象转化为字节流,以便用来实现存储或者传输。
反序列化,就是根据从文件或者网络上获取到的对象的字节流,根据字节流里面保存的对象描述信息和状态重新构建一个新的对象。
其次呢,序列化的前提是保证通信双方对于对象的可识别性,所以很多时候,我们会把对象转化为通用的解析格式,比如json、xml等。然后再把它们转化为数据流进行网络传输,从而实现跨平台和跨语言的可识别性。
最后,关于序列化的选择,开源的序列化技术非常多,比如Xml,Json,Thrift,Protobuf等
XML(可扩展标记语言)
优点:人机可读性好,可指定元素或特性的名称。
缺点:序列化数据只包含数据本身以及类的结构,不包括类型标识和程序集信息。只能序列化公共属性和字段,不能序列化方法。文件庞大,文件格式复杂,传输占带宽。
适用场景:当做配置文件存储数据,实时数据转换。
JSON(JS对象简谱,是一种轻量级的数据交换格式)
优点:兼容性高、数据格式比较简单,易于读写、序列化后数据较小,可扩展性好,兼容性好与XML相比,其协议比较简单,解析速度比较快。
缺点:数据的描述性比XML差、不适合性能要求为ms级别的情况、额外空间开销比较大。
适用场景(可替代XML):跨防火墙访问、可调式性要求高、基于Web browser的Ajax请求。传输数据量相对小,实时性要求相对低(例如秒级别)的服务。
Thrift(不仅是序列化协议,还是一个RPC框架)
优点:序列化后的体积小,速度快。支持多种语言和丰富的数据类型,对于数据字段的增删具有较强的兼容性,支持二进制压缩编码。
缺点:使用者较少,跨防火墙访问时不安全不具有可读性,调试代码时相对困难。不能与其他传输层协议共同使用(例如 HTTP),无法支持向持久层直接读写数据,即不适合做数据持久化序列化协议。
适用场景:分布式系统的RPC解决方案。
Protocol Buffers
将数据结构以.proto文件进行描述,通过代码生成工具可以生成对应数据结构的POJO对象和Protobuf相关的方法和属性。
优点:序列化后码流小,性能高、结构化数据存储格式(XML JSON 等)。通过标识字段的顺序,可以实现协议的前向兼容、结构化的文档 更容易管理和维护。
缺点:需要依赖于工具生成代码、支持的语言相对较少,官方只支持Java、C++、python。
适用场景:对性能要求高的RPC调用、具有良好的跨防火墙的访问属性、适合应用层对象的持久化。
JDK类库提供的序列化API:
java.io.ObjectOutputStream。表示对象输出流,其中writeObject(Object obj)方法可以将给定参数的obj对象进行序列化,将转换的一连串的字节序列写到指定的目标输出流中。
java.io.ObjectInputStream。该类表示对象输入流,该类下的readObject(Object obj)方法会从源输入流中读取字节序列,并将它反序列化为一个java对象并返回。
java.io.Serializable。是一个标志性接口,标识可以在JVM中进行序列化,JVM会为该类自动生成一个序列化版本号。参与序列化与反序列化的类必须实现Serializable接口。
private static final long serialVersionUID = 1234L。类属性,序列化版本号,用于给JVM 区别同名类,没有提供版本号,JVM会默认提供序列化版本号。
transient。关键字,当序列化时,不希望某些属性参与,则可以使用这个关键字标注该属性。
需要注意的是,被序列化的Java对象必须实现Serializable接口,否则会抛出NotSerializableException异常。另外,序列化和反序列化的Java对象必须是同一版本,否则会出现InvalidClassException异常。
Java序列化的步骤如下:
创建一个实现Serializable接口的Java对象。
创建一个ObjectOutputStream对象,将该对象写入字节流中。
关闭ObjectOutputStream对象。
Java反序列化的步骤如下:
创建一个ObjectInputStream对象。
从ObjectInputStream对象中读取字节流。
使用readObject()方法将字节流转换为Java对象。
关闭ObjectInputStream对象。
但在实际应用里面,序列化组件的选择,我认为有几个关键因素。
1.序列化之后的数据大小,因为数据大小会影响传输性能。
2.序列化的性能,序列化耗时较长会影响业务的性能。
3.是否支持跨平台和跨语言。
4.技术的成熟度,越成熟的方案使用的公司越多,也就越稳定。
猜你喜欢
- 2024-11-04 快速处理Kafka反序列化错误(kafka自定义反序列化)
- 2024-11-04 又一个反序列化漏洞,我服了...(反序列化漏洞修复方案)
- 2024-11-04 Java代码示例:如何使用 serialVersionUID处理序列化
- 2024-11-04 Java 序列化机制(java序列化过程)
- 2024-11-04 SpringBoot整合Grpc实现跨语言RPC通讯
- 2024-11-04 php和java及python3.10的序列化和反序列化
- 2024-11-04 Java修炼终极指南:133 避免在反序列化时发生DoS攻击
- 2024-11-04 聊聊fastjson反序列化的那些坑(fastjson反序列化原理)
- 2024-11-04 Java序列化 3 连问,这太难了吧(在线序列化工具)
- 2024-11-04 避免使用Java序列化(serializable 防止序列化)
你 发表评论:
欢迎- 最近发表
- 标签列表
-
- java反编译工具 (77)
- java反射 (57)
- java接口 (61)
- java随机数 (63)
- java7下载 (59)
- java数据结构 (61)
- java 三目运算符 (65)
- java对象转map (63)
- Java继承 (69)
- java字符串替换 (60)
- 快速排序java (59)
- java并发编程 (58)
- java api文档 (60)
- centos安装java (57)
- java调用webservice接口 (61)
- java深拷贝 (61)
- 工厂模式java (59)
- java代理模式 (59)
- java.lang (57)
- java连接mysql数据库 (67)
- java重载 (68)
- java 循环语句 (66)
- java反序列化 (58)
- java时间函数 (60)
- java是值传递还是引用传递 (62)
本文暂时没有评论,来添加一个吧(●'◡'●)