Csharp/C#教程:当所有关于大量任务分享


当所有关于大量任务

我需要你的帮助才能找到最佳解决方案。 这是我的原始代码:

public async Task Test() { var tasks = new List(); string line; using (var streamReader = File.OpenText(InputPath)) { while ((line = streamReader.ReadLine()) != null) { tasks.Add(Process(line)); } } await Task.WhenAll(tasks.ToArray()); } private Task Process(string line) { return Task.Run(() => { Console.WriteLine(line); }); } 

它将读取带有行的文件并按任务处理每一行。 但是,如果文件有100万行,那么任务数组就更大了,这段代码还是不错的? 或者我应该找到另一个解决方案 请帮我。 谢谢。

这是一个坏主意。 这可能会启动太multithreading。

更好的方法是简单地使用Parallel.ForEach()如下所示:

 using System; using System.IO; using System.Threading.Tasks; namespace Demo { static class Program { static void Main() { string filename = @"Your test filename goes here"; Parallel.ForEach(File.ReadLines(filename), process); } private static void process(string line) { Console.WriteLine(line); } } } 

但是,这不使用async / await。 但是如果你愿意的话,你可以在一个任务中将整个调用包装到Parallel.ForEach()中。

或者,如果要使用任务并行库 (Microsoft NuGet包),您可以执行以下操作:

 using System; using System.IO; using System.Threading; using System.Threading.Tasks; using System.Threading.Tasks.Dataflow; namespace Demo { static class Program { static void Main() { Task.Run(test).Wait(); } static async Task test() { string filename = @"Your filename goes here"; await processFile(filename); } static async Task processFile(string filename) { var options = new ExecutionDataflowBlockOptions { MaxDegreeOfParallelism = 8, BoundedCapacity = 100 }; var action = new ActionBlock(s => process(s), options); foreach (var line in File.ReadLines(filename)) await action.SendAsync(line); action.Complete(); await action.Completion; } static void process(string line) { Thread.Sleep(100); // Simulate work. Console.WriteLine(Thread.CurrentThread.ManagedThreadId + " " + line); } } } 

这为您提供了async支持。


附录 :线程池限制的演示。

(这是对shay __的评论的回应。)

如果您启动了许多长时间运行的任务,其中任务运行的时间比一秒钟大,那么您可能会看到线程池限制。

如果当前进程的ThreadPool.GetMinThreads(out workers, out ports);数等于或超过调用ThreadPool.GetMinThreads(out workers, out ports);返回的worker数,则会发生这种情况ThreadPool.GetMinThreads(out workers, out ports);

如果发生这种情况,在创建新的线程池线程之前,新的线程池线程的启动将延迟一小段时间(在我的系统上一秒钟)。 通常,这将允许另一个线程池线程变为可用,并且将使用它(当然这是限制的主要原因)。

以下代码演示了此问题:

 int workers, ports; ThreadPool.GetMinThreads(out workers, out ports); Console.WriteLine("Min workers = " + workers); // Prints 8 on my system. var sw = Stopwatch.StartNew(); for (int i = 0; i < 100; ++i) { Task.Run(() => { Console.WriteLine($"Thread {Thread.CurrentThread.ManagedThreadId} started at time {sw.Elapsed}"); Thread.Sleep(10000); }); } Console.ReadLine(); 

在我的系统上,这将打印以下内容:

 Min workers = 8 Thread 3 started at time 00:00:00.0098651 Thread 6 started at time 00:00:00.0098651 Thread 8 started at time 00:00:00.0099841 Thread 5 started at time 00:00:00.0099680 Thread 7 started at time 00:00:00.0099918 Thread 4 started at time 00:00:00.0098739 Thread 10 started at time 00:00:00.0100828 Thread 9 started at time 00:00:00.0101833 Thread 11 started at time 00:00:01.0096247 Thread 12 started at time 00:00:02.0098105 Thread 13 started at time 00:00:03.0099824 Thread 14 started at time 00:00:04.0100671 Thread 15 started at time 00:00:05.0098035 Thread 16 started at time 00:00:06.0099449 Thread 17 started at time 00:00:07.0096293 Thread 18 started at time 00:00:08.0106774 Thread 19 started at time 00:00:09.0098193 Thread 20 started at time 00:00:10.0104156 Thread 3 started at time 00:00:10.0109315 Thread 8 started at time 00:00:10.0112171 Thread 7 started at time 00:00:10.0112531 Thread 9 started at time 00:00:10.0117256 Thread 4 started at time 00:00:10.0117920 Thread 10 started at time 00:00:10.0117298 Thread 6 started at time 00:00:10.0109381 Thread 5 started at time 00:00:10.0112276 Thread 21 started at time 00:00:11.0095859 Thread 11 started at time 00:00:11.0101189 Thread 22 started at time 00:00:12.0095421 Thread 12 started at time 00:00:12.0111173 Thread 23 started at time 00:00:13.0095932 ... 

注意前8个线程如何快速启动,但随后新线程被限制为每秒一个,直到第一批线程终止然后可以重用。

另请注意,仅当线程需要相对较长的时间才能终止时,才会出现此效果。

上述就是C#学习教程:当所有关于大量任务分享的全部内容,如果对大家有所用处且需要了解更多关于C#学习教程,希望大家多多关注—计算机技术网(www.ctvol.com)!

本文来自网络收集,不代表计算机技术网立场,如涉及侵权请联系管理员删除。

ctvol管理联系方式QQ:251552304

本文章地址:https://www.ctvol.com/cdevelopment/959067.html

(0)
上一篇 2021年11月23日
下一篇 2021年11月23日

精彩推荐