首页
学习
活动
专区
圈层
工具
发布
社区首页 >问答首页 >为什么Java反序列化是受CPU限制的?

为什么Java反序列化是受CPU限制的?
EN

Stack Overflow用户
提问于 2012-04-10 23:18:17
回答 2查看 3.1K关注 0票数 5

我有一个Java程序,它在内存中将数据准备成相当复杂的大数据结构(几GB),并将其序列化到磁盘,另一个程序在内存中读回序列化的数据结构。我惊讶地注意到反序列化步骤相当慢,而且它是受CPU限制的。( top中的CPU使用率为100%,但iotop的读取速度仅为3到5 MB/s,对于硬盘驱动器上的顺序读取而言,这是非常低的)。CPU相当新(Core i7-3820),结构适合内存,没有配置交换空间。

为何会这样呢?有没有其他方法可以在Java中序列化对象,而不是将CPU作为瓶颈?

以下是反序列化代码,以防万一:

代码语言:javascript
复制
FileInputStream f = new FileInputStream(path);
ObjectInputStream of = new ObjectInputStream(f);
Object obj = of.readObject();
EN

回答 2

Stack Overflow用户

回答已采纳

发布于 2012-04-10 23:34:56

反序列化是非常昂贵的。如果你使用泛型反序列化,它将使用大量的反射和创建对象。

有很多更快的选择,而且大多数都使用生成的代码而不是反射。

http://code.google.com/p/thrift-protobuf-compare/wiki/Benchmarking

您会注意到,最快的方法之一是使用Externalizable,这可能是您的一个选择。这意味着为对象的序列化和反序列化添加自定义方法。

我已经编写了更快的方法,但这避免了通过回收它们或就地使用文件中的数据来创建任何对象(即不需要反序列化它们)

票数 4
EN

Stack Overflow用户

发布于 2012-04-10 23:35:51

如果不使用分析器查看,或者不了解对象结构的实际层次结构,就很难说出这一点,但我假设,如果它“相当复杂”,并且大约“几GB”大,那么您可能正在处理数千个单独的对象。

我最好的猜测是,Java反射会扼杀您的性能。反射用于从流构造对象,众所周知,这至少比直接在代码中调用构造函数慢两个数量级。因此,如果您的对象有大量的“小”对象,反射将花费大量时间重新构建它们。

您可以尝试的一件事(如果您还没有尝试过)是在每个Serializable类的顶部声明以下行:

代码语言:javascript
复制
private static final long serialVersionUID = [some number]L;

如果不声明这个ID,Java将不得不计算它,因此可以通过声明它来节省一些CPU周期。

如需进一步参考:

http://oreilly.com/catalog/javarmi/chapter/ch10.html

票数 2
EN
页面原文内容由Stack Overflow提供。腾讯云小微IT领域专用引擎提供翻译支持
原文链接:

https://stackoverflow.com/questions/10091505

复制
相关文章

相似问题

领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档