如何在使用TPL时管理线程本地存储(TLS)?

Eri*_*k T 10 .net asynchronous threadpool task-parallel-library thread-local-storage

我想在TLS中存储日志记录上下文信息,以便我可以在入口点设置一个值,并在所有结果栈中提供该值.这项工作很好,但我也使用TPL和ThreadPool.然后问题就变成了如何将TLS数据迁移到其他线程.我自己可以做到这一切,但后来我失去了像Parallel.For这样的好方法.

使用TPL时是否有某种方法可以复制TLS?当它获得await功能时,这也将适用于C#.

谢谢,埃里克

Ree*_*sey 5

通常,这是通过使用Parallel.For的重载来处理的,因为它已经提供了线程本地数据.

这个重载允许你提供一个初始化和一个终结委托,它有效地成为你的线程本地数据的每个线程的初始化,并在最后将一个简化函数"合并"在一起(每个线程运行一次). 我在这里详细介绍了这一点.

基本形式是做类似的事情:

object sync = new object();
double result = 0;

Parallel.For(0, collection.Count, 
    // Initialize thread local data:
    () => new MyThreadSpecificData(),
    // Process each item
    (i, pls, currentThreadLocalData) => 
    {
        // Generate a NEW version of your local state data
        MyThreadSpecificData newResults = ProcessItem(collection, i, currentThreadLocalData);
        return newResults;
    },
    // Aggregate results
    threadLocalData =>
    {
       // This requires synchronization, as it happens once per thread, 
       // but potentially simultaneously
       lock(sync)
          result += threadLocalData.Results;
    });
Run Code Online (Sandbox Code Playgroud)