3

我正在对映射的项目进行性能测试/优化

a document <--> Java object tree <--> mysql database

用于映射的文档、Java 类、数据库模式和逻辑是使用 HyperJaxb3 编排的。其中的ORM部分是hibernate提供的JPA。

大约有 50 个不同的实体,它们之间显然有很多关系。该应用程序的一个主要功能是加载文档,然后将数据重组为新文档;每个传入文档的所有部分最终都会在一个传出文档中发送出去。虽然我不希望生活在关系世界中,但事务语义非常适合这个应用程序 - 涉及大量资金和政府监管,因此我们需要确保所有内容都准确交付一次。

从功能上讲,一切进展顺利,性能也不错(经过大量调整)。每个文档由几千个实体组成,最终在数据库中创建几千行。文档的大小各不相同,插入性能与需要插入的行数几乎成正比(这并不奇怪)。

我看到了重大优化的潜力,这就是我的问题所在。

每个文档都映射到实体树。树的“叶子”一半包含许多详细信息,这些信息在决定如何生成传出文档时未使用。换句话说,我不需要能够通过许多表的内容来查询/过滤。

我想将适当的实体子树映射到 blob,从而节省插入/更新/索引我目前以通常方式处理的大多数行的开销。

看来我最好的选择是实现一个自定义 EntityPersister 并将其与适当的实体相关联。这是正确的方法吗?hibernate 文档还不错,但它是一个相当复杂的类,需要实现,在查看 javadoc 后我留下了很多问题。您能否指出一个具体但简单的示例,我可以将其用作起点?

关于另一种方法来处理这种优化的想法?

4

1 回答 1

1

我在存储大量二进制数据时遇到了同样的问题。我发现效果最好的解决方案是对象模型的非规范化。例如,我创建了一个主记录,然后创建了第二个保存二进制数据的对象。在 master 上,使用@OneToOne到辅助对象的映射,但将关联标记为惰性。现在只有在需要时才会加载数据。

可能会减慢您速度的一件事是outer join休眠对这种类型的所有对象执行。为避免这种情况,您可以将对象标记为强制对象。但是,如果数据库没有给您带来巨大的性能影响,我建议您不要管它。我发现如果我尝试进行常规连接,Hibernate 倾向于立即加载二进制数据。

最后,如果您需要在单个 SQL 调用中检索大量二进制数据,请使用 HQLfetch join命令。例如: from Article a fetch join a.data其中 a.data 是与二进制持有者的一对一关系。HQL 编译器会将其视为在单个 sql 调用中获取所有数据的指令。

高温高压

于 2013-01-18T01:33:09.807 回答