我正在阅读C# 5.0 in nutshell
并且在阅读了作者的观点之后,我对我应该采用什么感到很困惑。我的要求是说我有一个非常长时间运行(计算量很大)的任务,例如,计算数百万个文件的 SHA1(或其他)哈希,或者真的任何其他东西计算量很大并且可能需要一些时间,我的开发方法应该是什么(winforms
如果重要的话,使用 VS 2012,C# 5.0)so that I can also report progress to the user
,.
想到以下场景......
创建一个
Task
(with选项,通过实现或让任务捕获上下文并发布到UILongRunning
来计算哈希并向用户报告进度。IProgess<T>
Progess<T>
SynchronizationContext
创建一个
Async
类似的方法async CalculateHashesAsync() { // await here for tasks the calculate the hash await Task.Rung(() => CalculateHash(); // how do I report progress??? }
使用 TPL(或 PLINQ)作为
void CalcuateHashes() { Parallel.For(0, allFiles.Count, file => calcHash(file) // how do I report progress here? }
使用生产者/消费者队列。
真不知道怎么办?
书中的作者说...
在池线程上运行一个长时间运行的任务不会造成麻烦。当您并行运行多个长时间运行的任务(尤其是那些阻塞的任务)时,性能可能会受到影响。在这种情况下,通常有比 TaskCreationOptions.LongRunnging 更好的解决方案
- 如果任务是 IO 绑定的,TaskCompletionSource 和异步函数允许您使用回调而不是线程来实现并发。
- 如果任务是计算绑定的,生产者/消费者队列可以让您限制这些任务的并发性,避免其他线程和进程的饥饿。
关于Producer/Consumer
作者说...
生产者/消费者队列在并行编程和一般并发场景中都是一种有用的结构,因为它可以让您精确控制一次执行多少工作线程,这不仅对限制 CPU 消耗很有用,而且对其他资源也很有用。
那么,我不应该使用任务,这意味着第一个选项已经退出了吗?第二个是最好的选择吗?还有其他选择吗?如果我要遵循作者的建议,并实施生产者/消费者,我将如何做到这一点(我什至不知道如何在我的场景中开始使用生产者/消费者,如果这是最好的方法! )
我想知道是否有人遇到过这种情况,他们将如何实施?如果不是,那么最有效和/或易于开发/维护的性能是什么(我知道这个词performance
是主观的,但让我们考虑一下它工作的非常普遍的情况,并且工作得很好!)