java自有的序列化功能, 性能不怎么好,生产的字节也也偏大, 而且多语言之间不能通用。就自己花了几天时间,开发出了一个自动化序列化java对象。
原理是通过放射获取对象的信息,然后通过模板生产静态序列化和反序列化代码。
这个项目的优点是:
1, 对要序列化的对象项目无侵入。
2, 可以自定制。因为序列化和反序列化代码是自动生产了,可以随便修改。
3, 保持pojo的干净型
项目目前只支持一些常用类型。对象间的引用还不支持。特别是循环引用
说下性能吧!
理论上应该是很高的(没使用任何反射和动态代理)。与avro进行了对比, 发现序列化时, 比avro略低, 但是反序列化又略高。哈哈,很奇怪呀
生产的二进制字节要比avro大,通过int变形压缩后, 相差变小。
最后说下,这个为什么要有这个做这个项目吧!
不管是thrift, avro, google buffer, 它们都是很好的序列化工具,当做独立模块使用都很好, 但是与项目结合起来的时候,就存在对象间的转化问题。而且在使用也存在一些小缺陷。
附件中为代码,运行
SerializedTest
可以看到代码的性能。
在优化性能方面, 发现:
stream < ByteBuffer < byte[] 性能依次变差。
但是本人坚持简洁开发,因此使用的还是stream。 代码开发简洁很多。 但是性能也变慢。 (如果改成byte数组, 序列化和反序列化都要比avro强)
请看样例:
MakerConfig config = new MakerConfig();
config.className("ldh.LdhUser");
String basePath = "E:\\project\\ldh\\avro-test\\StupidBear\\src\\test\\java"; //代码生成路径
Maker maker = new Maker(config, basePath);
maker.create();
以上代码是对ldh.LdhUser生成序列化类。
最后生成了: ldh.LdhUserSerialize //静态类
序列化: public static byte[] ldh.LdhUserSerialize.toBytes(LdhUser user);
反序列化:public static LdhUser ldh.LdhUserSerialize.toObject(byte[] bytes);
性能测试:
对象User, json格式: {"name": "test-100", "age": 100, "id": 1000, "createTime": 123232323232, "address":["address-0", "address-1", "address-2", "address-3"], "props":{"key-0":"value-0", "key-1":"value-1"....., "key-9":"value-9"}}
序列化的大小:
avro length: 204 (avro 序列化后的大小)
ldh length: 249 (自动生成后的大小)
simple length: 292 (硬编码)
自动序列化变大有以下几个原因:
1, 对象可以为空(avro不能为空), 每一个属性添加了一字节进行是否为空标识(这样就多增加了20个字节)。
序列化性能对比: (对对象User进行: 100, 1000, 5000, 10000, 100000 序列化
ldh time:1, avro time:1, simple time:0
ldh time:10, avro time:7, simple time:9
ldh time:67, avro time:42, simple time:33
ldh time:103, avro time:69, simple time:68
ldh time:990, avro time:701, simple time:716
反序列化性能对比:
ldh time:0, avro time:1, simple time:1
ldh time:5, avro time:8, simple time:4
ldh time:26, avro time:44, simple time:20
ldh time:51, avro time:100, simple time:44
ldh time:536, avro time:890, simple time:408