我可以使用Task.Delay作为计时器吗?

时间:2017-02-14 07:07:00

标签: c# multithreading asynchronous timer task

我想在每一秒执行一些代码。我现在使用的代码是:

  

Task.Run((动作)ExecuteSomething);

ExecuteSomething() 的定义如下:

 private void ExecuteSomething()
        {
            Task.Delay(1000).ContinueWith(
               t =>
               {
                   //Do something.

                   ExecuteSomething();
               });
        }

此方法是否阻止线程?或者我应该在C#中使用Timer类?似乎Timer also dedicates a separate thread for execution(?)

3 个答案:

答案 0 :(得分:14)

Task.Delay在内部使用Timer

使用Task.Delay,您可以使代码比Timer更清晰。使用async-await不会阻止当前线程(通常是UI)。

public async Task ExecuteEverySecond(Action execute)
{
    while(true)
    {
        execute();
        await Task.Delay(1000);
    }
}

来自源代码:Task.Delay

// on line 5893
// ... and create our timer and make sure that it stays rooted.
if (millisecondsDelay != Timeout.Infinite) // no need to create the timer if it's an infinite timeout
{
    promise.Timer = new Timer(state => ((DelayPromise)state).Complete(), promise, millisecondsDelay, Timeout.Infinite);
    promise.Timer.KeepRootedWhileScheduled();
}

// ...

答案 1 :(得分:5)

Microsoft的Reactive Framework非常适合这种情况。只需NuGet“System.Reactive”获取位。然后你可以这样做:

IDisposable subscription =
    Observable
        .Interval(TimeSpan.FromSeconds(1.0))
        .Subscribe(x => execute());

如果您想停止订阅,请拨打subscription.Dispose()。除此之外,Reactive Framework可以提供比任务或基本计时器更强大的功能。

答案 2 :(得分:0)

static class Helper
{
    public async static Task ExecuteInterval(Action execute, int millisecond, IWorker worker)
    {
        while (worker.Worked)
        {
            execute();

            await Task.Delay(millisecond);
        }
    }
}


interface IWorker
{
    bool Worked { get; }
}