繁体   English   中英

Windows服务任务-轮询取消

[英]Windows Service Task - Polling Cancellation

我正在编写Windows服务,并发现了一个示例,该示例建议如下编写轮询Windows服务:

private void Poll()
{
    CancellationToken cancellationPoll = ctsPoll.Token;
    while (!cancellationPoll.WaitHandle.WaitOne(tsInterval))
    {
        PollDatabase();
        // Occasionally check the cancellation state.
        if (cancellationPoll.IsCancellationRequested)
        {
            break;
        }
    }
}

我对取消感到有些困惑,如果我同时需要cancelPoll.WaitHandle.WaitOne()和cancelPoll.IsCancellationRequested还是他们做着同样的事情,而只需要一个?

!cancellationPoll.WaitHandle.WaitOne(tsInterval)可以确保轮询间隔,因此在tsIntetval轮询之间至少要有tsIntetval (+操作持续时间):

--tsInterval--|--operation--|--tsInterval--|...

如果您查看CancellationToken.WaitHandle的文档,则会显示以下内容:

取消令牌时发出的WaitHandle信号。

因此,在您的情况下,操作cancellationPoll.IsCancellationRequested就足够了,因为它之后没有任何内容。 但是想象一下这样的情况:

while (!cancellationPoll.WaitHandle.WaitOne(tsInterval))
{
    //long operation A

    if (cancellationPoll.IsCancellationRequested)
    {
        break;
    }

    //long operation B

    if (cancellationPoll.IsCancellationRequested)
    {
        break;
    }
    //long operation C
}

在这种情况下,偶尔检查取消状态以避免长时间运行很有意义。

需要!cancellationPoll.WaitHandle.WaitOne(tsInterval) ,以便您不必一直等待。 WaitOne(tsInterval)将返回,因为令牌取消了WaitOne(tsInterval)令牌以使其取消或时间已用完。 如果令牌接收到取消信号,则WaitOne(tsInterval)将返回true然后结束循环。

例如,如果您要执行以下操作:

while(true)
{
    // long operation
    if (cancellationPoll.IsCancellationRequested)
    {
        break;
    }

    Thread.Sleep(tsInterval);
}

如果在线程被Thread.Sleep()阻塞时要求取消,则整个操作直到Thread.Sleep()完成并且if语句进入下一个循环时才知道需要取消。

等待WaitHanlde在这里是多余的,因为从结果的角度来看,它的作用与IsCancellationRequested相同-指示请求取消(但执行方式略有不同)。 因此,对于您的情况,您可以选择单个方法: WaitHandleIsCancellationRequested 但是请记住, WaitHandleIDisposable并且需要处理关联的CancellationTokenSource 如果您选择使用IsCancellationRequested请不要忘记添加一个调用,该调用应该重新安排诸如Thread.Sleep线程,以免过度利用CPU资源。 可以应用WaitHanlde一种情况是,当您需要等待句柄并且想向这种等待引入取消语义时:

 WaitHandle.WaitAny(new [] { handleToWait, cancellationHandle });

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM