How to track .Net thread pool usage?

自闭症网瘾萝莉.ら 提交于 2021-01-27 02:39:08

问题


AFAIK some methods in the .Net library are able to do I/O jobs asynchronously without consuming a thread from the pool.

If my information are correct the WebClient *Async methods do that.

I'd like to verify it by checking that effectively threads from the pool are not used during a download.

So my general question is : how can I monitor the current state of the thread-pool?

  • number of threads

  • number of busy threads

Is there some API (GetAvailableThreads?) or performance counters that would give this information?


EDIT: here are some more details

I'm writing a simple benchmark for educational purposes:

string[] urls = Enumerable.Repeat("http://google.com", 32).ToArray();
/*{
    "http://google.com",
    "http://yahoo.com",
    "http://microsoft.com",
    "http://wikipedia.com",
    "http://cnn.com",
    "http://facebook.com",
    "http://youtube.com",
    "http://twitter.com"
};*/

/*Task.Run(() =>
    {
        while (true)
        {
            int wt, cpt;
            ThreadPool.GetAvailableThreads(out wt, out cpt);
            Console.WriteLine("{0} / {1}", wt, cpt);
            Thread.Sleep(100);
        }
    });*/

WebClient webClient = new WebClient();
Stopwatch stopwatch = Stopwatch.StartNew();
foreach (string url in urls)
{
    webClient.DownloadString(url);
    Console.WriteLine("Got '{0}'", url);
}
stopwatch.Stop();

TimeSpan sequentialTime = stopwatch.Elapsed;

stopwatch.Restart();
CountdownEvent cde = new CountdownEvent(1);
foreach (string url in urls)
{
    cde.AddCount();
    webClient = new WebClient();
    webClient.DownloadStringCompleted += (_, __) =>
    {
        Console.WriteLine("Got '{0}'", __.UserState);
        cde.Signal();
    };
    webClient.DownloadStringAsync(new Uri(url), url);
}
cde.Signal();
cde.Wait();
stopwatch.Stop();

TimeSpan asyncTime = stopwatch.Elapsed;

stopwatch.Restart();
ThreadLocal<WebClient> threadWebClient = new ThreadLocal<WebClient>(() => new WebClient());
urls.AsParallel().WithDegreeOfParallelism(urls.Length).ForAll(url => threadWebClient.Value.DownloadString(url));
stopwatch.Stop();

TimeSpan PLinqTime = stopwatch.Elapsed;

Console.WriteLine("Sequential time: {0}.", sequentialTime);
Console.WriteLine("PLinq time: {0}.", PLinqTime);
Console.WriteLine("Async time: {0}.", asyncTime);

I'm comparing :

  • naive sequential loop
  • PLINQ loop
  • async I/Os

The interesting part are the last two.

I expect and try to prove that async I/Os are:

  • faster because they will create less pressure on the pool (less threads need to be created...)

  • lighter because they will consume less thread of the pool

My "benchmark" shows that it's faster and I guess that's because the pool does not need to allocate new threads for each request whereas with PLINQ each parallel request will block one thread.

Now I'd like to check the numbers about thread consumption.

The commented task was a poor attempt to monitor the pool. It may be the good starting point but until now the result are not really consistent with what I expect: it never displays that more than 3/4 threads are consumed, whereas I expect something like 32 threads busy.

I'm open to any idea to enhance it or better any other use-case that would clearly highlight the differences between the two approaches.

Hope this is clearer now, and sorry for not having provided the details sooner. :)


回答1:


The ThreadPool class provides the GetAvailableThreads method which "Retrieves the difference between the maximum number of thread pool threads returned by the GetMaxThreads method, and the number currently active." [1]: http://msdn.microsoft.com/en-us/library/system.threading.threadpool.getavailablethreads%28v=vs.110%29.aspx

You can capture the ratio thustly:

        int workerThreads;
        int completionPortThreads;
        ThreadPool.GetAvailableThreads(out workerThreads, out completionPortThreads);
        Console.WriteLine("{0} of {1} threads available", workerThreads, completionPortThreads);


来源:https://stackoverflow.com/questions/20109849/how-to-track-net-thread-pool-usage

易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!