gpt4 book ai didi

java - Hibernate批量保存嵌套对象

转载 作者:行者123 更新时间:2023-12-01 08:48:52 27 4
gpt4 key购买 nike

我有以下类结构:

class A{
int id;
List<B> blist;
List<C> clist;
List<D> dlist;
}

我得到一个 json 作为输入,它由映射器映射到对象A。现在,我有对象 A,其中包含 B、C 和 D 对象的列表。我想使用批处理来节省插入时间。我浏览了documentation其中描述了如果我想保存多个父对象的解决方案。在我的情况下,我将如何使用批处理功能,该情况具有多种类型的对象的嵌套列表。

我已使用启用批量插入

<property name="hibernate.jdbc.batch_size">50</property>

除非我清除并刷新 session ,否则这本身不会给我任何批处理。关于如何处理这个问题有什么建议吗?

最佳答案

问题在于您使用的是 IDENTITY 策略。

每当你保存一个新实体时,Hibernate 都会将它放入 Session 的 1LC 中;然而,为了做到这一点,必须知道标识符。 IDENTITY 策略的问题在于 Hibernate 必须实际执行插入以确定标识符值。

最后,批量插入功能被禁用。

您应该尝试使用预先已知的业务键值加载数据,或者在更坏的情况下使用带有序列优化器的SEQUENCE生成类型,以最大限度地减少数据库命中。这将允许批量插入工作。

更新

如果您没有定义行唯一性的业务键,并且您的数据库没有 SEQUENCE 支持,您可以自行管理标识符。您可以选择使用自定义标识符生成器来执行此操作,也可以仅在循环中作为代码执行此操作。

这里需要注意的是,此解决方案不是线程安全的。您应该保证在任何时候都不会在两个线程中同时运行此逻辑,这通常不会在批量数据加载时执行。

  1. 定义一个变量来存储您的标识符。我们需要根据数据库中标识符的现有最大值来初始化该变量。如果数据库中不存在任何行,我们可能希望将其初始化为 1。

    Long value = ... // createQuery ( "SELECT MAX(id) FROM YourEntity" )
    value = ( value == null ? 1L : value + 1);
  2. 下一步是更改 @Id 带注释的字段。它不应该被标记为@GenerateValue,因为我们将允许应用程序提供该值。

  3. 对于要插入的每一行,只需使用步骤 1 中生成的 value 变量调用 #setId( value ) 方法即可。

  4. value 变量增加 1。

关于java - Hibernate批量保存嵌套对象,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/42514406/

27 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com