如何等待多个 C# 事件?
Posted
技术标签:
【中文标题】如何等待多个 C# 事件?【英文标题】:How to wait for multiple C# events? 【发布时间】:2020-08-31 21:01:03 【问题描述】:我想为以下问题找到一个好的解决方案。 例如,我有 5 个计时器,我从 1 个线程开始。这些计时器在几秒钟后完成它们的工作(这是一种重试机制)。我想等待所有的计时器完成他们的工作。
所以问题是,有什么好的模式可以解决这个问题吗?或者你现在是不是一个布尔集合的好解决方案,如果所有元素都是真的,那么所有的计时器都完成了:D
提前感谢您的回答!
【问题讨论】:
你启动了多少个定时器? "...我有 5 个计时器..." - 一定是错字,好吧,有 5 个计时器。 "...这些计时器..." - 哦,看起来实际上有 1 个计时器。 " 完成他们的 工作" - 不,5 个计时器。 “...这是一个重试机制...” - 嗯,5个重试机制的计时器?我想它实际上是一个计时器。 “...等待所有计时器...” - 哦,伙计:( @vasily.sib 尽管有错字,但仍有 2 人理解我的问题 :) 下次我会更加注意,我保证;) 【参考方案1】:这听起来你真的想使用Task
而不是Timer
。
愚蠢的例子:
async Task DoAsync()
var allTheWork = new [] Work(), Work(), Work() ;
await Task.WhenAll(allTheWork);
// Did all the sub-tasks return true?
if (allTheWork.All(i => i.Result))
async Task<bool> Work()
var retries = 3;
while (retries-- > 0)
if (success) return true;
await Task.Delay(2000); // This is the timer; you can find better retry patterns of course
return false;
【讨论】:
这正是我想要的。非常感谢。 @Xsayar 当你做Task.WhenAll(tasks)
intellitect.com/catching-exceptions-tasks-whenall时要小心异常处理【参考方案2】:
您的问题有多种解决方案。
如果您熟悉 linq,我建议您看一下 Rx(反应式扩展),因为它们使用非常相似的语法。 Rx 允许您对各种事件做很多事情。
另一种方法是使用TPL(任务并行库)如下:
var timer1 = Task.Delay(1000);
var timer2 = Task.Delay(2000);
var timer3 = Task.Delay(3000);
await Task.WhenAll(timer1, timer2, timer3);
请注意,您必须从异步上下文中调用它。如果您不熟悉 async/await,我建议您看一下。如果您不想/不能看它,您可以简单地执行以下操作:
Task.WhenAll(timer1, timer2, timer3).GetAwaiter().GetResult();
【讨论】:
我可以从这个答案中使用“GetAwaiter().GetResult()”。这是一个巨大的帮助,谢谢,这有助于理解。以上是关于如何等待多个 C# 事件?的主要内容,如果未能解决你的问题,请参考以下文章