在 ThreadPool 线程之间传递数据

Passing data between ThreadPool threads

我有一个 C# 网络服务器,我一直在使用 Whosebug miniprofiler 对其进行分析。因为它不是 ASP.NET 服务器,但每个请求通常都在其自己的线程上执行,所以我将 miniprofiler 设置为使用 ThreadStatic 存储从头到尾跟踪传入请求的所有分析器。这很好用。

最近我们将所有内容都转换为使用 async/await,这意味着 await 之后的延续通常不会回到相同的 Thread,因此 ThreadStatic 存储不再有效。

在这种情况下,在不同 ThreadPool 线程之间传递一些小数据的最佳方法是什么?是否有现有的 SynchronizationContext 实现可用于类似这样的事情?

What's the best way to pass some small piece of data between different ThreadPool threads in this case?

通过 CallContext class. It exposes two static methods: LogicalSetData and LogicalGetData 使用逻辑调用上下文。调用上下文通过 ExecutionContext 存储和编组,它还负责同步上下文等

使用此 class 有两个限制:

  1. 您只能使用 .NET 4.5 及更高版本

  2. 逻辑调用上下文使用写时复制语义,并在数据发生变异后执行浅拷贝。这意味着您应该只使用不可变数据,因为引用可能会在多个线程之间共享。

最后要注意的是 CallContext 只有在您调用它时才会初始化。这意味着在使用它时,由于写时复制,您会承担一些开销。

更多信息可以在 Stephan Cleary 的 post 中找到,名为 Implicit Async Context