【发布时间】:2015-08-24 17:28:47
【问题描述】:
我不确定对我的代码中的事件做出反应的两种可能性。大多数情况下,我担心哪一个需要更少的资源。
我有一个注册到eventproducer 的观察者的方法。如果eventproducer返回了一些东西,方法退出,方法的调用者再次启动方法(你可以把它想象成一种长轮询)。
eventproducer 有时每秒会触发很多事件,有时会暂停几分钟。
第一种方法是等待 500 毫秒的延迟,然后检查是否有要返回的内容,否则(直到超时 5 分钟)再次延迟 500 毫秒。
eventProducer.RegisterListener((events)=>{evList.Add(events)});
while(evList.Count=0 && !TimeOut){
await Task.Delay(500);}
eventProducer.UnRegister(...);
// return evList, method gets recalled immediately
第二种方法是使用CancellationToken。如果eventproducer 产生某些东西,CancellationTokenSource 会取消源。在方法中我等待Task.Delay(5min, cancellationToken)。
eventProducer.RegisterListener((events)=>{evList.Add(events);
cancelSource.Cancel();}
try
{
await Task.Delay(5min, cancellationToken)
}
catch(TaskCanceledException){//nothing to do};
eventProducer.UnRegister(...);
// return evList, method gets recalled immediately
第二种方法的优点是,如果生产者产生了某些东西,该方法会立即返回,并且我们不必在循环中等待和唤醒。
但是对于第二种方法,每次生产者生产某些东西时,都会抛出一个TaskCanceledException。我担心这可能会影响系统负载,而不是唤醒和等待每 500 毫秒,尤其是当eventproducer 产生大量事件时。
我是否高估了抛出和捕获异常的成本?有没有办法用CancellationToken 取消Task.Delay 但不抛出TaskCanceledException? IE。类似task.setComplete?
【问题讨论】:
-
它只是“更长的时间”的占位符
标签: c# asynchronous exception-handling async-await task-parallel-library