Parallel.ForEachを読んでも新しいスレッドが生成され続けますが、それが同時実行スレッドの数をカウントする正しい方法であるかどうかはまだ疑問です。
私が見ているのは、メソッドが で同時に入力されたが完了していない反復 (ループ) の数をカウントしていることですParallel.ForEach
。
同時に実行されるスレッドの正しい数を伝える同時スレッド数の同義語ですか?
私は専門家ではありませんが、次のように想像できます。
- 後で続行するためにそのアクティビティがどこかでスワップされている間、スレッドを再利用できます。
- 理論的には、ループ アクティビティに関与しているスレッドは、ループの完了後もスレッド プールに保持されますが、別のアクティビティに再利用されることはありません。
- または、(スレッド数の) 実験の純粋性を歪める可能性は何ですか?
とにかく、できれば(C#)コードで、.NETプロセスの実行中のスレッドの量を直接カウントする方法は?
アップデート:
したがって、 Jeppe Stig Nielsenの回答に従って、カウントに使用する場合
directThreadsCount = Process.GetCurrentProcess().Threads.Count;
出力は、リリース (threadsCount == 7) モードとデバッグ (threadsCount == 15) モードの両方で非常に似ています。
[Job 0 complete. 2 threads remaining but directThreadsCount == 7
[Job 1 complete. 1 threads remaining but directThreadsCount == 7
[Job 2 complete. 2 threads remaining but directThreadsCount == 7
[Job 4 complete. 2 threads remaining but directThreadsCount == 7
[Job 5 complete. 2 threads remaining but directThreadsCount == 7
[Job 3 complete. 2 threads remaining but directThreadsCount == 7
[Job 6 complete. 2 threads remaining but directThreadsCount == 7
[Job 9 complete. 2 threads remaining but directThreadsCount == 7
[Job 7 complete. 1 threads remaining but directThreadsCount == 7
[Job 8 complete. 0 threads remaining but directThreadsCount == 7
FINISHED
つまり、スレッドの数が減少することはなく、上記の方法が正しくないことをSystem.Diagnostics.ProcessThread
示しています。"Class name is not valid at this point"
私の結論は正しいですか、なぜできないのですか?ProcessThread
使用
C# コンソール アプリケーションの使用コード:
using System;
using System.Collections.Generic;
using System.Diagnostics;
using System.Linq;
using System.Threading;
using System.Threading.Tasks;
namespace Edit4Posting
{
public class Node
{
public Node Previous { get; private set; }
public Node(Node previous)
{
Previous = previous;
}
}
public class Edit4Posting
{
public static void Main(string[] args)
{
int concurrentThreads = 0;
int directThreadsCount = 0;
int diagThreadCount = 0;
var jobs = Enumerable.Range(0, 10);
Parallel.ForEach(jobs, delegate(int jobNr)
{
int threadsRemaining = Interlocked.Increment(ref concurrentThreads);
int heavyness = jobNr % 9;
//Give the processor and the garbage collector something to do...
List<Node> nodes = new List<Node>();
Node current = null;
//for (int y = 0; y < 1024 * 1024 * heavyness; y++)
for (int y = 0; y < 1024 * 24 * heavyness; y++)
{
current = new Node(current);
nodes.Add(current);
}
//*******************************
//uncommenting next line gives: "Class name is not valid at this point"
//diagThreadCount=System.Diagnostics.ProcessThread
directThreadsCount = Process.GetCurrentProcess().Threads.Count;
//*******************************
threadsRemaining = Interlocked.Decrement(ref concurrentThreads);
Console.WriteLine(
"[Job {0} complete. {1} threads remaining but directThreadsCount == {2}",
jobNr, threadsRemaining, directThreadsCount);
});
Console.WriteLine("FINISHED");
Console.ReadLine();
}
}
}