为啥线程数达到 MinThreads 限制后 ThreadPool.QueueUserWorkItem 很慢? [复制]
Posted
技术标签:
【中文标题】为啥线程数达到 MinThreads 限制后 ThreadPool.QueueUserWorkItem 很慢? [复制]【英文标题】:Why ThreadPool.QueueUserWorkItem is slow after thread count reach the limit of MinThreads? [duplicate]为什么线程数达到 MinThreads 限制后 ThreadPool.QueueUserWorkItem 很慢? [复制] 【发布时间】:2021-07-19 11:05:23 【问题描述】:class Program
static void DoIt(string name)
Console.WriteLine($"DateTime.Now, Threadname started");
Thread.Sleep(50000);
Console.WriteLine($"DateTime.Now, Threadname done");
static void Main()
//ThreadPool.SetMinThreads(100, 100);
for (int i = 0; i < 100; i++)
int value = i;
ThreadPool.QueueUserWorkItem((s) =>
string name = value.ToString();
DoIt(name);
);
Console.ReadKey();
程序的结果: result
2021/4/26 11:26:23,线程 2 开始 2021/4/26 11:26:23, Thread0 开始 2021/4/26 11:26:23,线程1开始 2021/4/26 11:26:23,Thread3 开始 2021/4/26 11:26:24,Thread4 启动 2021/4/26 11:26:25,Thread5 启动 2021/4/26 11:26:26,Thread6 启动 2021/4/26 11:26:27,Thread7 启动 2021/4/26 11:26:28,Thread8 启动 2021/4/26 11:26:29,Thread9 开始
同时启动 100 个线程。前 4 个线程非常快。后面的线程每秒启动一个,直到一些工作线程完成。
-
为什么前 4 个线程很快?
我电脑的cpu核心数是4。如果程序运行在8核或32核的电脑上,前8或32个线程快,其他慢。
如果 SetMinThreads 为 100,则所有 100 个线程都快速启动
如果我不 SetMinThreads,为什么后面的线程启动这么慢?
【问题讨论】:
GetMaxThreads 返回什么值? 【参考方案1】: .NET 线程池将提供线程,直到达到最小值 (ThreadPool.GetMinThreads),没有任何延迟。 之后,线程池可以等待任务完成(队列)或创建新线程(直到达到 ThreadPool.GetMaxThreads) 没有记录 ThreadPool 何时创建新线程的实际算法,因为它不断发展。但这取决于它运行的硬件和它计算的一堆统计数据。 通过将 SetMinThreads 设置为 100,您实际上是在告诉 .NET 线程池提供 100 个线程,没有任何问题。这就是线程快速启动的原因。 将 MinThreads 设置为较高的值有其自身的缺点 ...(您应该会看到内存使用量增加,因为每个线程都需要有自己的内存用于调用堆栈等,并且当您达到更高数量的线程时,处理器将花更多时间只做上下文切换而不是实际处理) minthreads 的默认值取决于内核数量和 .net 框架版本。这就是为什么当您迁移到不同的硬件时,行为会发生变化。【讨论】:
本来想说的基本一样。打算为ThreadPool
source 添加一个链接,以说明线程池可能很复杂,并且可以解释如何处理最小/最大线程数。以上是关于为啥线程数达到 MinThreads 限制后 ThreadPool.QueueUserWorkItem 很慢? [复制]的主要内容,如果未能解决你的问题,请参考以下文章