C# ut同步。当前的lock语句没有任何作用。@jeroenmoster:说得好。我更新了我的建议。请注意我答案的更新。@StriplingWarrior:我知道OP没有问这个问题,但是锁定GetPrimeNumbers调用违背了线程的目的,因为现在每个线程都

C# ut同步。当前的lock语句没有任何作用。@jeroenmoster:说得好。我更新了我的建议。请注意我答案的更新。@StriplingWarrior:我知道OP没有问这个问题,但是锁定GetPrimeNumbers调用违背了线程的目的,因为现在每个线程都,c#,multithreading,C#,Multithreading,ut同步。当前的lock语句没有任何作用。@jeroenmoster:说得好。我更新了我的建议。请注意我答案的更新。@StriplingWarrior:我知道OP没有问这个问题,但是锁定GetPrimeNumbers调用违背了线程的目的,因为现在每个线程都必须排在前面的线程后面。@RobertHarvey:同意。请参阅我文章末尾的建议,它根本不会锁定。@Ted Elliott:Task.Run()是异步的还是它会生成多个线程?@DwightSchrute Task.Run会在线程池中对工作进行排


ut同步。当前的
lock
语句没有任何作用。@jeroenmoster:说得好。我更新了我的建议。请注意我答案的更新。@StriplingWarrior:我知道OP没有问这个问题,但是锁定
GetPrimeNumbers
调用违背了线程的目的,因为现在每个线程都必须排在前面的线程后面。@RobertHarvey:同意。请参阅我文章末尾的建议,它根本不会锁定。@Ted Elliott:Task.Run()是异步的还是它会生成多个线程?@DwightSchrute Task.Run会在线程池中对工作进行排队,这可能会导致使用多个线程。请注意我答案的更新。@StriplingWarrior:我知道OP没有问这个问题,但是在
GetPrimeNumbers
调用周围锁定会破坏线程的用途,因为每个线程现在都必须在前面的线程后面排队。@RobertHarvey:同意。请参阅我文章末尾的建议,它根本不锁定。@Ted Elliott:Task.Run()是异步的还是它会生成多个线程?@DwightSchrute Task.Run将在线程池上对工作进行排队,这可能会导致使用多个线程。
    static void Main(string[] args)
    {
            var sw = new Stopwatch();
            sw.Start();

            int noOfThreads = Environment.ProcessorCount;
            //int minVal = 1;
            int maxVal = 10000000;
            int  blockSize = maxVal / noOfThreads;
            List<Thread> threads = new List<Thread>();
            List<List<int>> results = new List<List<int>>();
            object thisLock = new object();

            for (int i = 0; i < noOfThreads; ++i)
            {
                lock(thisLock)
                {
                    Thread th = new Thread(() =>
                    {
                        results.Add(GetPrimeNumbers(i * blockSize, i * blockSize + blockSize));
                    });

                    th.Start();
                    threads.Add(th);
                }
            }

            foreach (var elem in threads)
                elem.Join();
   }

   private static List<int> GetPrimeNumbers(int low, int high)
   {
        List<int> result = new List<int>();
        //Debug.WriteLine("Low: {0}. High: {1}", low, high);
        for(int i = low; i <= high; ++i)
        {
            if (IsPrime(i))
                result.Add(i);
        }

        return result;
    }

    static bool IsPrime(int number)
    {
        if (number % 2 == 0)
            return false;
        else
        {
            var topLimit = (int)Math.Sqrt(number);
            for (int i = 3; i <= topLimit; i += 2)
                if (number % i == 0) 
                    return false;

            return true;
        }
    }
for (int i = 0; i < noOfThreads; ++i)
{
    int j = i; // capture the value
    lock(thisLock)
    {
        Thread th = new Thread(() =>
        {
            results.Add(GetPrimeNumbers(j * blockSize, j * blockSize + blockSize));
        });

        th.Start();
        threads.Add(th);
    }
}
var allPrimeNumbers = Enumerable.Range(0, numberOfThreads)
    .AsParallel()
    .SelectMany(i => GetPrimeNumbers(i * blockSize, i * blockSize + blockSize))
    .ToList();
for (int i = 0; i < noOfThreads; ++i)
{
    int j = i; // capture the value
    Thread th = new Thread(() =>
    {
        result = GetPrimeNumbers(j * blockSize, j * blockSize + blockSize);
        lock(thisLock) 
        {
           results.Add(result);
        }
    });

    th.Start();
    threads.Add(th);
}
Task<List<int>> tasks = new Task<List<int>>();
for (int i = 0; i < noOfThreads; ++i)
{
    int j = i; // capture the value
    tasks.Add(Task.Run(() => GetPrimeNumbers(j * blockSize, j * blockSize + blockSize)));
}

Task.WaitAll(tasks);
results = tasks.Select(t => t.Result).ToList();