在java中以多线程方式插入或更新数据库中的多条记录

Posted

技术标签:

【中文标题】在java中以多线程方式插入或更新数据库中的多条记录【英文标题】:Inserting or updating multiple records in database in a multi-threaded way in java 【发布时间】:2011-09-22 08:05:53 【问题描述】:

我正在更新数据库中的多条记录。现在,每当 UI 发送要更新的记录列表时,我只需更新数据库中的这些记录。我正在为此使用 JDBC 模板。

早期案例

早先,每当我从 UI 获取记录时,我都会这样做

jdbcTemplate.batchUpdate(Query, List<object[]> params)

每当出现异常时,我都会回滚整个事务。

已更新:batchUpdate 是多线程的还是在某些方面比批处理更新更快?)

后期案例

但后来每当出现异常时,需求就会发生变化。因此,每当出现异常时,我应该知道哪些记录未能更新。所以我不得不将记录发送回 UI,以防出现异常并说明为什么失败。

所以我不得不做类似的事情:

for(Record record : RecordList)

   try
       jdbcTemplate.update(sql, Object[] param)
   catch(Exception ex)
       record.setReason("Exception : "+ex.getMessage());
       continue;
   

那么我是否以正确的方式通过使用循环来执行此操作?

如果是,有人可以建议我如何使其成为多线程。 或者在这种情况下有什么问题。 说实话,我很犹豫在循环中使用 try catch 块:(。

请指正,真的需要学习更好的方法,因为我自己觉得,一定有更好的方法,谢谢。

【问题讨论】:

与其在涉及相同行的单独线程中进行批量更新,不如尝试以不冲突的方式在线程之间拆分工作? 【参考方案1】:

将所有更新操作设为可调用集合, 将其发送到 java.util.concurrent.ThreadPoolExecutor。池是多线程的。

使可调用:

class UpdateTask implements Callable<Exception> 
  //constructor with jdbctemplate,sql,param goes here.
  @Override
    public Exception call() throws Exception 
        try
              jdbcTemplate.update(sql, Object[] param)
            catch(Exception ex)
                   return ex;
           

        return null;
    

调用调用:

<T> List<Future<T>> java.util.concurrent.ExecutorService.invokeAll(Collection<? extends Callable<T>> tasks) throws InterruptedException

【讨论】:

【参考方案2】:

您的情况看起来您需要在java中使用验证并单独过滤掉有效数据并发送到数据库进行更新。

BO layer -> filter out the Valid Record. -> Invalid Record should be send back with some validation text.

在 DAO 层 -> 批量更新您的 RecordList

这将为您提供最佳性能。

永远不要使用数据库插入异常作为验证机制。

    异常代价高昂,因为必须创建堆栈跟踪 与数据库的连接是另一个成本高昂的过程,需要花费一些时间才能建立连接 Java If-Else 在相同的数据库验证中运行得更快

【讨论】:

是的,我同意你的所有观点,但我的朋友,我没有验证逻辑。例外是我们无法想到代码可能会失败的情况。不过谢谢,不适用于我的情况。 @kinshuk4 1st 我会尝试在验证中捕获最大的已知问题。然后我会期待我们无法预测的未知原因的例外。仍然对于您的情况,您可以做一件事,您可以同时拥有两种实现&lt;batch insert logic&gt; on exception &lt;call individual insert logic&gt;。不确定代码审查团队是否会对逻辑感到满意

以上是关于在java中以多线程方式插入或更新数据库中的多条记录的主要内容,如果未能解决你的问题,请参考以下文章

在bigquery中以编程方式更新/插入数据

在 Python 的 REST API 程序中以多进程方式调用方法而苦苦挣扎

如果 mysql 数据库中的表中不存在,则更新或插入多条记录

如何在 NextJS 中以多步形式传递数据?

在 bigquery 中以编程方式更新/插入数据

多线程环境中的 PetaPoco 事务