将交易范围添加到Parallel.Foreach [英] Adding Transaction Scope to Parallel.Foreach

查看:69
本文介绍了将交易范围添加到Parallel.Foreach的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我有一个循环将记录插入数据库(Firebird):

I have a loop inserting records into a database (Firebird):

using (TransactionScope scope = new TransactionScope(TransactionScopeOption.Required, options))
{
    taskList.Add(Task.Factory.StartNew(() =>
    {       
        Parallel.ForEach(objectList, c =>
        {
            DoInsert(c, id);
        });
    }));

    scope.Complete()
}

如果插入失败,我希望能够将这些插入作为一批回滚.但是,当我在Parallel.Foreach循环中执行插入操作时,事务范围不可见.我假设这是因为循环在不同的线程中运行.如果我使用TransactionScope作为串行插入来执行此操作,则一切正常.

I would like the ability to rollback these inserts as a batch if the insert fails. However as I'm performing the insert within a Parallel.Foreach loop, the transaction scope isn't visible. I'm assuming that's because the loop is operating in a different thread. If I do this as a serial insert using TransactionScope, everything works.

我尝试使用DependentTransaction,但似乎无法获得DoInsert函数的上下文. DoInsert只需打开一个连接并将C的内容写入数据库.

I've tried to use a DependentTransaction but I can't seem to get the context to the DoInsert function. The DoInsert simply opens a connection and writes the contents of C to the database.

有什么想法吗?

谢谢

推荐答案

由于提到的原因,您不能使用单个TransactionScope来执行此操作:TransactionScope依赖于线程本地存储,并且您处于多线程环境中.

You cannot do this using a single TransactionScope, for the reason you mentioned: TransactionScope relies on threadlocal storage, and you are in a multithreaded environment.

但更重要的是,要使其正常工作,每个工作线程都需要打开一个连接,将其加入分布式事务中,进行插入,然后关闭连接.

But more importantly, for this to work, every worker thread would need to open a connection, enlist it in a distributed transaction, do the insert, and close the connection.

如果这是简单的插入,那么创建所有这些连接将给您带来任何性能优势,我会感到非常惊讶.实际上,我相信如果您在单个线程和单个连接上执行此程序,它将更快.显然,这意味着该连接被打开(和关闭)一次,并作为参数传递给DoInsert方法.

If this are simple inserts, I'd be very surprised that creating all these connections would give you any performance benefit. In fact, I believe this program would be a lot faster if you did it on a single thread, and on a single connection. Obviously, that implies that the connection is opened (and closed) once, and passed into the DoInsert method as a parameter.

更好的是,您可能希望查看批量插入.

Even better, you might want to look at bulk insert.

这篇关于将交易范围添加到Parallel.Foreach的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆