我有一个 Elapsed 方法,其中有一个 while 循环。如果计时器从另一个线程被禁用/停止,我希望这个循环停止。我可以依赖 Elapsed 方法中计时器的 Enabled 属性,还是应该创建一个“volatile bool timerEnabled”变量来确定。我的测试表明它没问题,但我想在将它投入生产之前确定这一点。
这就是我想要实现的(不是实际代码,而是关闭)
private volatile bool isElapsedAlreadyRunning
void myTimer_Elapsed(object sender, ElapsedEventArgs e)
{
if (!isElapsedAlreadyRunning) // to prevent reentrance
{
isElapsedAlreadyRunning = true;
try
{
while (myTimer.Enabled && some other condition)
{
do stuff
}
}
finally
{
isElapsedAlreadyRunning = false;
}
}
}
myTimer.Start() and myTimer.Stop() are in other methods that can be called frrom other threads
我正在使用 System.Timers.Timer 类
如果您有任何其他意见或看到此设计中的任何陷阱,请随时发表评论:)
谢谢
编辑 :
伙计,穿线很难。根据答案和其他stackoverflow问题(特别是这个答案),这将是做到这一点的方法(我希望这次没问题)
public class NoLockTimer : IDisposable
{
private readonly System.Timers.Timer _timer;
private bool _isTimerStopped = false;
private readonly object _isTimerStoppedLock = new object();
public NoLockTimer()
{
_timer = new System.Timers.Timer { AutoReset = false, Interval = 1000 };
_timer.Elapsed += delegate
{
try
{
while (!IsTimerStopped && some other condition)
{
// do stuff
}
}
catch (Exception e)
{
// Do some logging
}
finally
{
if (!IsTimerStopped)
{
_timer.Start(); // <- Manual restart.
}
}
};
_timer.Start();
}
public void Stop()
{
IsTimerStopped = true;
if (_timer != null)
{
_timer.Stop();
}
}
private bool IsTimerStopped
{
get
{
lock (_isTimerStoppedLock)
{
return _isTimerStopped;
}
}
set
{
lock (_isTimerStoppedLock)
{
_isTimerStopped = value;
}
}
}
public void Dispose()
{
Stop();
if (_timer != null)
{
_timer.Dispose();
}
}
}