我正在使用Threading.Timer
,例如:
new Timer(new TimerCallback(y=>
{
try
{
Save(Read(DateTime.Now));
// here i want to dispose this timer
}
catch
{
}
}),null,100000,10000);
如何在回调中处理此计时器。或解决方法? 更新:让我解释一下情况。我想尝试调用方法“保存”,同时抛出异常。如果有效,我需要停止计时器。
答案 0 :(得分:14)
试试这个:
Timer timer = null;
timer = new Timer(new TimerCallback(y =>
{
try
{
Save(Read(DateTime.Now));
// here i want to dispose this timer
timer.Dispose();
}
catch
{
}
}));
timer.Change(10000, 10000);
修改强>
我根据Chuu的建议稍微修改了上面的代码。请注意,如果通过不同的计时器事件同时调用TimerCallback,Timer.Dispose
可能最终被调用多次。幸运的是,Timer
并不关心它是否被多次处理。
答案 1 :(得分:2)
这是一种更好的方法。当您使用只有一个参数(TimerCallback)的构造函数时,传递给回调的状态将是计时器本身。
Timer timer = new Timer(o =>
{
((Timer)o).Dispose();
//Your code here
});
//Start the timer
timer.Change(100000,10000);
以下是msdn docs的一个例子:
public void StartTimer(int dueTime)
{
Timer t = new Timer(new TimerCallback(TimerProc));
t.Change(dueTime, 0);
}
private void TimerProc(object state)
{
// The state object is the Timer object.
Timer t = (Timer) state;
t.Dispose();
Console.WriteLine("The timer callback executes.");
}
http://msdn.microsoft.com/en-us/library/ms149618(v=vs.110).aspx
答案 2 :(得分:1)
您需要将计时器的引用保留在变量中 -
public class MyClass
{
private Timer _timer;
public void StartTimer()
{
_timer = new Timer(new TimerCallback(y=>{
try
{
Save(Read(DateTime.Now));
_timer.Dispose();
}
catch {
}
}),null,100000,10000);
}
}
注意:这是未经测试的代码。请检查它是否有效并更新。
答案 3 :(得分:0)
您必须在某处存储对计时器的引用,并将其作为状态传递给计时器对象本身。尝试创建类似这样的类:
public class TimerContainer
{
public Timer Timer { get; set; }
}
然后在你的方法中使用它:
Action<object> tcb = state =>
{
var container = (TimerConatiner)state;
try
{
Save(Read(DateTime.Now));
container.Timer.Dispose();
}
catch
{
// whatever...
}
};
var container = new TimerContainer();
container.Timer = new Timer(tcb, container, 100000, 10000);
答案 4 :(得分:0)
如果您使用多线程或多任务处理,请小心!如果是这样,这里你是CancelAfter方法扩展器(.net 4.0)的代码和解决方案:
private static object syncObj = new object();
public static void CancelAfter(this CancellationTokenSource source, int timeoutMilliseconds, Action code = null)
{
if (timeoutMilliseconds == 0) return; // No timeout
if (source == null)
{
throw new NullReferenceException();
}
if (timeoutMilliseconds < -1)
{
throw new ArgumentOutOfRangeException("timeout");
}
Timer timer = new Timer(delegate(object self)
{
lock (syncObj)
{
try
{
if (null != code)
code.Invoke();
source.Cancel();
((IDisposable)self).Dispose();
}
catch (ObjectDisposedException)
{
}
}
});
timer.Change(timeoutMilliseconds, -1);
}
}
此致 Juanlu,ElGuerre