等待线程结束的问题

时间:2013-02-19 08:46:47

标签: c# multithreading join

我正在做一些C#线程。启动线程并将数据传输给它们没有问题,但我在等待它们结束时遇到问题。

我的代码如下所示。我正在使用Join()等待线程结束,但由于某种原因我的代码不起作用。

尽管在所有活动线程上调用Join(),主线程(即for循环)仍未被阻塞。

知道我做错了吗?

List<Thread> calculationThreads = new List<Thread>();

foreach (string calculation in calculations)
{
    if (calculationThreads.Count < 5)
    {
        Thread calculationThread = new Thread(DoCalculation);
        calculationThreads.Add(calculationThread);

        calculationThread.Start(threadData);
    }
    else
    {
        // Wait for the threads to complete
        foreach (Thread calculationThread in calculationThreads)
        {
            calculationThread.Join();
        }
    }   
}

4 个答案:

答案 0 :(得分:2)

第一个问题是您对else案件的处理。如果已经存在五个线程,则代码将等待线程完成,但是它尝试添加的任务从未添加。它只会抛弃这项任务并继续下一步。

第二个问题是你没有从列表中删除任何线程,所以一旦它到达五个线程,它将永远等待。如果第一个问题没有丢弃剩下的任务,那么你的程序就会锁定。

此外,在继续工作之前等待所有五个线程完成会浪费处理时间,但这是一个较小的问题。

答案 1 :(得分:0)

我会采用一些方法来计算我已经开始的线程数,并且在每个线程的末尾我减少了计数器。

然后在你的循环开始时你可以拥有

while(counter >= 5)
{
//Wait
}

答案 2 :(得分:0)

你可以有一个等待所有线程结束的while循环。

List<Thread> calculationThreads = new List<Thread>();

foreach (string calculation in calculations)
{
    if (calculationThreads.Count < 5)
    {
        Thread calculationThread = new Thread(DoCalculation);
        calculationThreads.Add(calculationThread);

        calculationThread.Start(threadData);
    }
    else
    {
        // Wait for the threads to complete
        while(calculationThread.Any(x => x.IsAlive)){}
        // Clearing the list
        calculationThread.Clear();
    }   
}

如果你想在for循环之后保留线程,你应该有另一个列表来存储线程。

答案 3 :(得分:0)

您为该方法提供了多少计算?

阅读代码,如果你提供4个计算,你将启动4个线程,但实际上从未进入你执行线程的代码。加入()。

将thread.join循环移到if else语句之外。

List<Thread> calculationThreads = new List<Thread>();

    foreach (string calculation in calculations)
    {
        if (calculationThreads.Count < 5)
        {
            Thread calculationThread = new Thread(DoCalculation);
            calculationThreads.Add(calculationThread);

            calculationThread.Start(threadData);
        }

    }
    foreach (Thread calculationThread in calculationThreads)
    {
        calculationThread.Join();
    }