c# – 任务MaxDegreeOfParallelism可以每次从我的列表中获取前n
我在我的函数中打开n个并发线程:
List<string> _files = new List<string>(); public void Start() { CancellationTokenSource _tokenSource = new CancellationTokenSource(); var token = _tokenSource.Token; Task.Factory.StartNew(() => { try { Parallel.ForEach(_files,new ParallelOptions { MaxDegreeOfParallelism = 5 //limit number of parallel threads },file => { if (token.IsCancellationRequested) return; //do work... }); } catch (Exception) { } },_tokenSource.Token).ContinueWith( t => { //finish... },TaskScheduler.FromCurrentSynchronizationContext() //to ContinueWith (update UI) from UI thread ); } 线程打开后,我注意到它从我的列表中选择了随机文件. 解决方法
要获得你想要的行为,你需要编写一个
custom partitioner,它看起来像“随机”的原因是它现在是在块中批处理文件列表所以如果你的源列表是
List<string> files = List<string> { "a","b","c","d","e","f","g","h","i" }; 当它分区时,它可以像这样均匀地分割它(如果Max是3个线程): > Thread1的工作清单:“a”,“b”,“c” 因此,如果你看过正在处理的文件,它可能看起来像 "a","i" 如果你创建一个自定义分区程序,你可以让它一次只取一个项目,而不是一次批处理,使工作列表看起来像 > Thread1的工作清单:“a”,GetTheNextUnprocessedString() 如果您使用的是.NET 4.5,则可以像这样使用this factory: Parallel.ForEach(Partitioner.Create(_files,EnumerablePartitionerOptions.NoBuffering),(file,loopstate,index) => { if (token.IsCancellationRequested) return; //do work... }); 如果您不使用.NET 4.5,这不是一项微不足道的任务,所以我不打算在这里为您编写.阅读我在顶部链接的MSDN文章,您最终可以找到它. 我会做的是问自己“我真的需要按顺序处理文件吗?”如果您不需要它们按顺序让它自己进行排序,因为您通过执行订单可能会做的唯一事情可能会减慢流程. (编辑:李大同) 【声明】本站内容均来自网络,其相关言论仅代表作者个人观点,不代表本站立场。若无意侵犯到您的权利,请及时与联系站长删除相关内容! |