Warning: file_get_contents(/data/phpspider/zhask/data//catemap/6/multithreading/4.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
C# 要使用多少线程?_C#_Multithreading_Visual Studio 2010_.net 4.0_Threadpool - Fatal编程技术网

C# 要使用多少线程?

C# 要使用多少线程?,c#,multithreading,visual-studio-2010,.net-4.0,threadpool,C#,Multithreading,Visual Studio 2010,.net 4.0,Threadpool,我知道存在一些问题,它们提供了一个很好的总体观点。我希望得到一些关于C#/VB.Net方面的细节,以便实际实现这些透视图(而不是哲学) 我的特殊情况 我有一个WCF服务,其中包括接收文件。在服务生命的大部分时间里,这一特定区域实际上只是坐在那里无所事事——当工作真的到来时,它会以大量不同的数量突然出现 对于接收到的每个文件(最高可达每秒数千个),服务需要在文件上工作1-10秒(每个),具体取决于许多其他服务、本地资源和网络IO等待时间 为了帮助服务处理这些突发工作负载,我实现了一个队列系统。每秒

我知道存在一些问题,它们提供了一个很好的总体观点。我希望得到一些关于C#/VB.Net方面的细节,以便实际实现这些透视图(而不是哲学)

我的特殊情况 我有一个WCF服务,其中包括接收文件。在服务生命的大部分时间里,这一特定区域实际上只是坐在那里无所事事——当工作真的到来时,它会以大量不同的数量突然出现

对于接收到的每个文件(最高可达每秒数千个),服务需要在文件上工作1-10秒(每个),具体取决于许多其他服务、本地资源和网络IO等待时间

为了帮助服务处理这些突发工作负载,我实现了一个队列系统。每秒接收的数千个文件被放入队列中。控制器根据队列的大小计算要使用的线程数,直到达到“峰值最大线程数”设置,该设置阻止它创建额外的线程。这些线程被放置在线程池中,并被重用以在队列中循环。控制员将:;每隔一段时间;重新计算所需的线程数。如果队列大小减小,将释放相应数量的线程

由来已久的问题 我应该达到多少线程的峰值?显然,每次收到一个文件时添加一个新线程是愚蠢的,因为没有更好的词——性能最好会恶化。当每个核心的CPU利用率只有10%时,给线程设置上限似乎也不是资源的最佳利用

那么,有没有合适的方法来确定要限制多少线程呢?我希望服务可以通过采样可用资源自行确定这一点,但这样做是否会影响性能?我知道常见的答案是监视工作负载,通过反复试验调整计数,直到找到我喜欢的数字,但由于这项服务的性质(长时间空闲,然后是高/突发工作负载),可能需要很长时间才能获得此类信息

那么,如果我们将服务器映像移动到与第一台主机更快/更慢/不同的另一台主机,该怎么办?我必须重新取样整个过程

理想情况下,我所追求的是协调人智能地增加线程池的大小,直到CPU利用率达到x%(80%合理吗?90%?99%?)。显然,我希望这样做,而不必添加比达到x%所需的更多线程,否则我最终得到的只是线程,而不仅仅是等待IO资源,而是相互等待

提前谢谢


相关问题(如果你想要一些一般性的想法):


你的麻烦事 如果我不让问题变得更难,哪里会有乐趣呢

目前的情况是,在这些突发事件中,该服务确实会定期达到100%的cpu。问题是CPU利用率峰值。它从空闲(0-10%)变为100%,然后再次下降。我不确定我能帮上忙——理想情况下,我不会一路走到100%。问题的存在是因为提到的文件实际上是图像,而服务的一部分过程是将图像传递到System.Windows.Media blackbox,后者为我执行一些复杂的图像处理

然后,由于IO等待和其他正在进行的处理,在峰值之间会出现停顿。如果达到100%的峰值无法得到帮助(我完全知道如何防止,或者如果我应该),我应该如何确定CPU利用率图表的目标?一直坐在100%的位置?在50-100之间跳跃?如果我真的进行了采样,以确定什么似乎最有效,是否可以保证在相同的图中切换虚拟服务器的主机也会最有效

对于那些愿意回答的人来说,这增加了复杂性,我不会考虑。请忽略此部分。然而,任何能解释这种复杂情况的答案,甚至只是提供如何处理它的提示的答案,我至少会投赞成票


这是一个很长的问题-很抱歉-谢谢你阅读了这么多

动态线程管理器如何监控其总体性能,并据此生成新线程或杀死旧线程?这里的主要问题只是如何定义性能度量函数。其余的可以通过定期调度的作业来完成,该作业根据之前的线程数量和性能增加或减少线程数量。也可能与资源利用率(CPU、磁盘、网络…)有关。

允许您查询处理器使用情况

但是,您是否尝试过框架提供的一些功能

        foreach (var file in files)
        {
            var workitem = file;
            Task.Factory.StartNew(() =>
            {
                // do work on workitem
            }, TaskCreationOptions.LongRunning | TaskCreationOptions.PreferFairness);
        }
您可以调整任务中任务的并发级别

默认情况下,.NET 4线程池将安排在其运行的硬件上运行性能最好的线程数,但您可以更改前一个链接的工作方式

也许您需要一个定制的解决方案,但可以用标准对您的解决方案进行基准测试

编辑:(注释):

不需要链接,我可能使用了一个虚构的术语,因为英语不是我的语言。我的意思是:有一个变量,在最后一次检查之前存储方差(prevDelta),并称之为delta。每次“检查”时,将其添加到变量avrageDelta并除以2。由于您没有活动,因此变量averageDelta通常较低。然后有另一组delta变量,一个已经存在的变量(delta-prevdta),并将其存储在一个delta变量中,该delta变量不是所有delta的平均值,而是一个小时间跨度内delta的平均值(您必须想出一个算法来精确计算这个时间方差)。完成此操作后,您可以比较平均值