首页 文章

指定默认的MaxDegreeOfParallelism会导致并行循环运行得更快

提问于
浏览
-1

我正在使用System.Threading.Tasks.Parallel.ForEach() . 出于某种原因将MaxDegreeOfParallelism设置为“-1”或甚至“50”,导致循环运行得更快(大约15秒并且它是一致的) . MaxDegreeOfParallelism参数的默认值为-1,将其设置为50或任何其他数字应该只使其变慢 . 可能是什么原因?

System.Collections.Concurrent.ConcurrentBag<FileDataInfo> filesData = new System.Collections.Concurrent.ConcurrentBag<FileDataInfo>();
        System.Threading.Tasks.Parallel.ForEach(filesInfo, 
            new System.Threading.Tasks.ParallelOptions() { MaxDegreeOfParallelism = -1 },
            info =>
        {
            if (!string.IsNullOrEmpty(info.FolderPath))
                info.FolderPath = System.IO.Path.Combine(dataPathDirName, info.FolderPath);
            else
                info.FolderPath = dataPathDirName;

            var storageHandler = FileStorageFactory.CreateStorageHander();
            byte[] data = storageHandler.GetFileData(info.FilePath);
            filesData.Add(new FileDataInfo() { Info = info, Data = data });
        });

2 回答

  • 1

    MaxDegreeOfParallelism 告诉TPL可以同时运行多少东西 . 这可以通过多种方式影响执行速度 . 通过将此值设置为较低的值,它允许任务在其自己的CPU / Core上运行 . 这使得事情运行得更快,因为你获得了良好的并行性 . 如果将此值设置得更高(或-1),那么您可以运行更多CPU /核心任务 . 当发生这种情况时,跨任务共享CPU所花费的时间可能会花费相当多的时间并使操作看起来更慢 .

    一般经验法则:不要将并行度设置为高于系统中核心/ CPU的数量 .

  • 1

    您的问题不受CPU限制,它受I / O限制 . 现代驱动器可以利用大量I / O来更有效地执行它 . 通过使用 Parallel.ForEach ,您可以填充此队列并使驱动器以最高效率运行 .

    虽然你可能会注意到这里的加速,但最好注意你创建了大量的线程来实现这一点 . 过多的线程几乎从来都不是一个好主意,因为它由于调度程序开销和缓存流失而变得非常低效 . 如果可能,我建议将代码转换为使用async和TPL数据流 . 这将允许您使用单个线程来管理大量并行I / O请求 .

相关问题