gpt4 book ai didi

c# - 线程与任务中的 ThreadStatic 属性

转载 作者:行者123 更新时间:2023-11-30 15:23:46 26 4
gpt4 key购买 nike

当我使用 ThreadStatic 属性探索线程和任务时,我遇到了一些奇怪的事情。我相信这可能非常特定于线程和任务。考虑以下代码片段:

[ThreadStatic]
static int range=10;


Action action = () =>
{Console.WriteLine("Thread = {0}, Value = {1}", Thread.CurrentThread.ManagedThreadId, range);

Parallel.Invoke( action, action);

这给出了输出:

Thread = 2, Value = 10 
Thread = 3, Value = 0

这绝对没问题,因为 ThreadStatic 变量只能初始化一次,所以第二行显示为 0。

但是,请考虑以下情况:

[ThreadStatic]
static int range=10;

new Thread(() =>
{
Console.WriteLine("Thread = {0}, Value = {1}" Thread.CurrentThread.ManagedThreadId, range);
}).Start();

new Thread(() =>
{
Console.WriteLine("Thread = {0}, Value = {1}" Thread.CurrentThread.ManagedThreadId, range);
}).Start();

这一行给我输出:

Thread = 6, Value = 0
Thread = 7, Value = 0

我跨越了多少线程,我无法真正看到“范围”值被初始化并显示为 10。这里初始化的范围变量在哪里以及为什么在初始化静态变量时线程和任务之间存在区别?

我是不是漏掉了一些基本的东西?提前致谢。

最佳答案

您的 [ThreadStatic] 由包含此代码的类的静态构造函数初始化。通过创建类实例或使用静态成员的线程,以先到者为准。所以根据定义,您创建的两个线程永远看不到初始值。

古怪的行为实际上是在第一个 片段中。您没有想到的是 Parallel.Invoke() 还使用调用 Invoke() 的线程来完成部分工作。所以它实际上可以看到初始值。稍微重写一下代码可以向您展示:

class Test {
[ThreadStatic]
static int range=10;

public static void Run() {
Action action = () => {
Console.WriteLine("Thread = {0}, Value = {1}", Thread.CurrentThread.ManagedThreadId, range);
};
Console.WriteLine("Start thread = {0}, Value = {1}", Thread.CurrentThread.ManagedThreadId, range);
Parallel.Invoke(action, action);
}
}

输出:

Start thread = 8, Value = 10
Thread = 8, Value = 10
Thread = 9, Value = 0

当然不是真正的问题,您不能在并行代码中使用 [ThreadStatic]。

关于c# - 线程与任务中的 ThreadStatic 属性,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/33971793/

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