c# – 在应用程序服务关闭停止之前等待定时器已过事件完成

c# – 在应用程序服务关闭停止之前等待定时器已过事件完成,第1张

概述概要: 在 Windows服务和控制台应用程序我正在调用一个公共库,其中包含定时器,定期触发大约需要30秒钟的 *** 作.不过这样做很好 当服务停止或应用程序退出被调用并且计时器在ElapsedEventHandler中时,我需要服务停止/应用程序退出等待直到事件处理程序完成. 我已经通过在调用定时器停止方法时检查一个Boolean InEvent属性来实现这个功能. 虽然这是功能,但问题是:这是最好的 概要:
在 Windows服务和控制台应用程序我正在调用一个公共库,其中包含定时器,定期触发大约需要30秒钟的 *** 作.不过这样做很好

当服务停止或应用程序退出被调用并且计时器在ElapsedEventHandler中时,我需要服务停止/应用程序退出等待直到事件处理程序完成.

我已经通过在调用定时器停止方法时检查一个Boolean InEvent属性来实现这个功能.

虽然这是功能,但问题是:这是最好的办法吗?是否有更好的方法可以更好地达到这个目的?

另一个问题是我需要避免服务停止请求失败,并显示“服务无法响应停止请求”

这是我的实现

public sealed class TimedProcess : Idisposable{    static TimedProcess singletonInstance;    bool InEvent;    Timer processtimer;    private TimedProcess()    {    }    public static TimedProcess Instance    {        get        {            if (singletonInstance == null)            {                singletonInstance = new TimedProcess();            }            return singletonInstance;        }    }    public voID Start(double interval)    {        this.processtimer = new Timer();        this.processtimer.autoreset = false;        this.processtimer.Interval = interval;        this.processtimer.Elapsed += new ElapsedEventHandler(this.processtimer_Elapsed);        this.processtimer.Enabled = true;    }    public voID Stop()    {        if (processtimer != null)        {            while (InEvent)            {            }            processtimer.Stop();        }    }    voID processtimer_Elapsed(object sender,ElapsedEventArgs e)    {        try        {            InEvent = true;            // Do something here that takes ~30 seconds        }        catch        {        }        finally        {            InEvent = false;            processtimer.Enabled = true;        }    }    public voID dispose()    {        if (processtimer != null)        {            Stop();            processtimer.dispose();        }    }}

这就是在OnStart / console应用程序main中调用的方法:

TimedProcess.Instance.Start(1000);

这是在服务OnStop和应用程序main(挂起的按键)中如何调用:

TimedProcess.Instance.Stop();
解决方法 可能最简单和最可靠的方法是使用监视器.创建主程序和定时器回调可以访问的对象:
private object _timerLock = new object();

您的主程序在关闭之前尝试锁定:

// wait for timer process to stopMonitor.Enter(_timerLock);// do shutdown tasks here

你的定时器回调也锁定它:

voID processtimer_Elapsed(object sender,ElapsedEventArgs e){    if (!Monitor.TryEnter(_timerLock))    {        // something has the lock. Probably shutting down.        return;    }    try    {        // Do something here that takes ~30 seconds    }    finally    {        Monitor.Exit(_timerLock);    }}

主程序一经获取就不应该释放锁.

如果您希望主程序在一段时间后继续关闭,无论是否获得锁定,请使用Monitor.TryEnter.例如,这将等待15秒.

bool gotLock = Monitor.TryEnter(_timerLock,TimeSpan.FromSeconds(15));

如果能够获得锁,则返回值为true.

顺便问一下,我强烈建议您使用System.Threading.Timer而不是System.Timers.Timer.后者阻止例外,最终可能会隐藏错误.如果您的Elapsed事件发生异常,它将永远不会被转义,这意味着您永远不会知道它.有关更多信息,请参阅我的blog post.

总结

以上是内存溢出为你收集整理的c# – 在应用程序/服务关闭/停止之前等待定时器已过事件完成全部内容,希望文章能够帮你解决c# – 在应用程序/服务关闭/停止之前等待定时器已过事件完成所遇到的程序开发问题。

如果觉得内存溢出网站内容还不错,欢迎将内存溢出网站推荐给程序员好友。

欢迎分享,转载请注明来源:内存溢出

原文地址: http://outofmemory.cn/langs/1241574.html

(0)
打赏 微信扫一扫 微信扫一扫 支付宝扫一扫 支付宝扫一扫
上一篇 2022-06-06
下一篇 2022-06-06

发表评论

登录后才能评论

评论列表(0条)

保存