我有一个Intel四核CPU。内核与我可以产生的线程数之间的关系
如果我要开发一个只用于我的机器上的Winforms应用程序(我使用C#btw),我可以产生多少个线程?
核心与我可以在任何时候运行的最大线程数有某种相关性吗?我是否需要找出有多少个线程在同一时间运行,如果是的话,这是可能的吗? (我知道有最小和最大线程的属性)?这是否依赖于线程池(该池中线程的最大数量是否更改?)。这是此帖子/线程的C#部分。
我有一个Intel四核CPU。内核与我可以产生的线程数之间的关系
如果我要开发一个只用于我的机器上的Winforms应用程序(我使用C#btw),我可以产生多少个线程?
核心与我可以在任何时候运行的最大线程数有某种相关性吗?我是否需要找出有多少个线程在同一时间运行,如果是的话,这是可能的吗? (我知道有最小和最大线程的属性)?这是否依赖于线程池(该池中线程的最大数量是否更改?)。这是此帖子/线程的C#部分。
这一切都取决于,如果你的线程是活跃的(而不是等待IO)100%的时间,那么每个CPU有更多的1线程是没有意义的。但是,除非您正在执行复杂的数值计算,否则很少出现这种情况。
.Nets线程池有:http://msdn.microsoft.com/en-us/library/system.threading.threadpool.aspx
线程池具有的每间可用 处理器 250工作线程,和1000 I/O完成 线程的默认大小。
所以,我会说,很少有建议任何人都可以给你,除了:
在当你添加更多的线程一些点东西会变慢,由于上下文切换和同步。
虽然线程和内核之间存在松散的相关性(线程真正并行执行的唯一方法是让它们在不同的内核上运行,但知识的价值低于您的想象),真正的工作由操作系统调度程序完成,在这种情况下是Windows中的线程调度程序。
至于有多少线程可以创建,这将随系统而异。 ThreadPool
类对产生自己的线程没有任何限制;它有一个线程池,它在内部管理自己。这些是您在检查ThreadPool
类的属性时可以看到的值。然而,这并不是说你应该产生无限的线程;最终操作系统将花费更多的时间在你的线程之间切换,而不是实际上允许线程运行。通过基准测试找出有多少线程适合您的应用程序。
你究竟想要做什么?
我可以产生多少线程?
Waaay,waaay更多(数百或数千倍)比你想产卵为最佳的吞吐量。
(在Windows上)每个线程的限制我所知道的是:
DOTNET大概增加了自己的东西,一堆每个线程的开销。 GC等。
一点式我喜欢使用一个WAG是:
threads = 2 * (cpu cores + active disk spindles)
最佳数量通常是两个,一个因子之内。那个。理论上说,需要的线程是cpu核心的主动(出于显而易见的原因),但也有些线程会阻塞磁盘I/O。乘以2会使CPU有些事情要做,而其他线程被阻塞。
无论如何,从那开始并测量它。工作线程的数量是后来调整整个问题最简单的部分,所以现在不要担心太多。
只是想知道什么限制将首先通过启动许多线程命中。我写了下面这个简单的测试程序并试了一下。现在我假设记忆是限制因素。我能够运行1000个线程,但没有Thread.Sleep()
,系统变得“没有反应”。 2000线程在1800线程左右启动后出现内存不足异常。 (笔记本具有英特尔Core 2 Duo T5800 2.0千兆赫,3.0吉布RAM和与.NET框架3.5 SP1上的Windows XP SP3运行 “几个” 应用程序)
UPDATE
的内存溢出异常是由一堆线程引起的。在线程构造函数中指定堆栈大小后(我使用了64 kB,但可能是目前我不知道的最小大小),我能够启动3500个线程(使用Thread.Sleep()
)。
using System;
using System.Linq;
using System.Threading;
namespace GeneralTestApplication
{
class Program
{
private static void Main()
{
Console.WriteLine("Enter the number of threads to start.");
while (!Int32.TryParse(Console.ReadLine(), out Program.numberThreads)) { }
Program.counters = new Int64[Program.numberThreads];
Console.WriteLine("Starting {0} threads.", Program.numberThreads);
for (Int32 threadNumber = 0; threadNumber < Program.numberThreads; threadNumber++)
{
new Thread(Program.ThreadMethod).Start(threadNumber);
}
Console.WriteLine("Press enter to perform work on all threads.");
Console.ReadLine();
Program.manualResetEvent.Set();
Console.WriteLine("Press enter to stop all threads.");
Console.ReadLine();
Program.stop = true;
Console.WriteLine("At least {0} threads ran.", Program.counters.Count(c => c > 0));
Console.ReadLine();
}
private static Int32 numberThreads = 0;
private static Int64[] counters = null;
private static readonly ManualResetEvent manualResetEvent = new ManualResetEvent(false);
private static volatile Boolean stop = false;
public static void ThreadMethod(Object argument)
{
Int32 threadNumber = (Int32)argument;
Program.manualResetEvent.WaitOne();
while (!Program.stop)
{
Program.counters[threadNumber]++;
// Uncomment to simulate heavy work.
Thread.Sleep(10);
}
}
}
}
您必须测量。也就是说,通过N核心,我通常在N + 1和2N线程之间产卵以获得最佳结果。但你必须测量。
你想要产生多少个线程?如果你完全担心任何限制,你可能会有太多限制。 – 2009-08-03 22:55:52
我没有产生任何。这是假想的和未来的(我很好奇,好奇,我问的很多问题都与我目前的发展无关)。我想知道这个理论。 – dotnetdev 2009-08-03 22:57:36