线程池中线程的可用性
本文关键字:线程 可用性 | 更新日期: 2023-09-27 18:05:12
如何从线程池中找到60%(或N%)的线程可用性?这背后的逻辑是什么?
父线程使用线程池线程生成多个url,并等待所有子线程完成。
代码如下:
父线程
public void Save()
{
List<Job> Jobs = PickJobs();
int workerThreads = 0,compThreads = 0;
ThreadPool.GetMinThreads(workerThreads, compThreads);
int requiredThreads = 15;
ThreadPool.SetMaxThreads(requiredThreads, compThreads);
WaitCallback waitCallBack = default(WaitCallback);
ManualResetEvent mEvent = default(ManualResetEvent);
foreach (Job _job in Jobs)
{
waitCallBack = new WaitCallback(CallBackFunc);
mEvent = new ManualResetEvent(false);
events.Add(mEvent);
ThreadPool.QueueUserWorkItem(waitCallBack, new UrlData(_job, mEvent, HttpContext.Current));
}
WaitHandle.WaitAll(events.ToArray(), 300000);//05 Minutes
}
子线程
private void CallBackFunc(object obj)
{
UrlData msgObj = (UrlData)obj;
WebRequest lWebRequest = WebRequest.Create(psUrl);
lWebRequest.Timeout = 60000;
WebResponse lWebResponse = lWebRequest.GetResponse;
msgObj.FinishEvent.Set();
}
跨线程通信的对象数据
public class UrlData
{
public Job job;
public ManualResetEvent FinishEvent;
public HttpContext HttpContextRef;
public UrlData(Job pJob, ManualResetEvent pEvent, HttpContext pContext)
{
job= pJob;
FinishEvent = pEvent;
HttpContextRef = pContext;
}
}
在上面的代码中,所需的线程被硬编码为:
int requiredThreads = 15;
ThreadPool.SetMaxThreads(requiredThreads, compThreads);
硬编码会导致线程池耗尽吗?如果线程池中没有可用的线程会发生什么?如何在托管服务器中找到线程池中可用的线程总数?
谢谢。
经过一番研究,我最终得到了一个最大线程计数检索功能。
它返回线程池中暂时可用的线程数。如果发生线程饥饿,则返回0。
/// <returns>int (Number of threads currently available)</returns>
private int GetMaxItemsRetrievalCount()
{
int rtnVal = 1;
try {
//Get Available idle threads currently in the thead pool.
ThreadPool.GetAvailableThreads(workerThreads, completionThreads);
rtnVal = workerThreads > MaxConcurrentThreads ? MaxConcurrentThreads : workerThreads;
//Math.Min(MaxConcurrentThreads - currentWorkLength, workerThreads - ThreadBuffer);
rtnVal = rtnVal > 0 ? rtnVal : 0;
} catch (Exception ex) {
WriteTransactionalJobLog(new JobLogDTO {
Mode = "Parallel",
UniqueId = "GetMaxItemsRetrievalCount Exception",
ThreadId = Thread.CurrentThread.ManagedThreadId.ToString(),
StartTime = DateTime.Now.ToString(),
ExceptionOrResult = ex.ToString()
});
}
return rtnVal;
}