C#,System.Timers.Timer,与系统时钟同步每分钟运行一次

C#,System.Timers.Timer,与系统时钟同步每分钟运行一次,c#,timer,system,sync,clock,C#,Timer,System,Sync,Clock,我试图让计时器每分钟与系统时钟同步运行(00:01:00、00:02:00、00:03:00等)。下面的代码会产生一个稳定的计时器吗?我试过运行它。计时器确实每分钟运行一次。但问题是,它会在几个月后开始漂移吗 private System.Timers.Timer timer; public frmMain() { timer = new System.Timers.Timer(); timer.AutoReset = false;

我试图让计时器每分钟与系统时钟同步运行(00:01:00、00:02:00、00:03:00等)。下面的代码会产生一个稳定的计时器吗?我试过运行它。计时器确实每分钟运行一次。但问题是,它会在几个月后开始漂移吗

private System.Timers.Timer timer;

public frmMain()
{
            timer = new System.Timers.Timer();
            timer.AutoReset = false;
            timer.Elapsed += new System.Timers.ElapsedEventHandler(timer_Elapsed);
            timer.Interval = GetInterval();
            timer.Start();
}

private void timer_Elapsed(object sender, System.Timers.ElapsedEventArgs e)
{
            //Do processing

            timer.Interval = GetInterval();
            timer.Start();

}
private double GetInterval()
{
            DateTime now = DateTime.Now;
            return ((60 - now.Second) * 1000 - now.Millisecond);
}
不会的


DateTime。现在
使用系统时钟作为参考计时器,因此您的计时器将始终与它保持同步,以系统时钟分辨率的几毫秒为单位。

我看不出它如何漂移,每次计时器滴答作响时,它都会确定到下一个精确分钟的时间长度,并相应地设置间隔。从理论上讲,它实际上是相当巧妙的,因为我的计时器本身会游走。确定的唯一方法当然是测试它,所以只要你的UI没有冻结超过60秒(为了安全起见可能是50秒),就不会有问题。请记住,笔记本电脑在放置一段时间后,或盖子关闭时,通常会进入睡眠状态,这将导致出现故障


但是,根据您试图执行的操作,为什么不使用系统时间,在每分钟发生变化时发送事件?

您的代码不会漂移,但会(不可避免地)出现抖动,因为计时器回调很少在请求的时间间隔上发生

我在这段代码中看到的唯一潜在问题是
ThreadPool
的压力太大,以至于计时器回调没有在一分钟内退出队列并执行,从而导致一分钟被跳过


这似乎有点不太可能,但并非完全超出了可能的范围。

总体情况看起来不错,
GetInterval
将始终返回正值,依此类推。我只看到几个警告:

  • 如果发生待机/恢复,则您可能会在非整周时间运行一次
  • 如果计时器的运行时间超过一分钟,则您将错过一个节拍
  • 如果系统负荷过大,计时器运行时间被安排为延迟40/50秒,并且计时器运行时间超过
    60-延迟
    秒,则您将错过一个节拍

  • 这取决于对你来说一分钟都不耽误有多重要,你期望你的预定操作能在多大程度上运行(最糟糕的时间),以及你想实现什么。正如比尔所说,解决方案取决于问题。如果你需要一天跑1440次(也就是每分钟跑一次),那么也许你应该记录它跑了多少次,以及它应该跑多少次。如果计时器需要每分钟运行一次,那么everybeat检查它是否在最后一分钟运行,如果这次没有运行两次等等…如果它正在轮询更新,那么您可以忽略跳过的节拍,等等。。。[顺便说一句,我的真名不是Bill xD]可能是同一用户的重复。