之间有什么区别吗?
System.Threading.Timer
System.Threading.Timer timer = new System.Threading.Timer(new TimerCallback(PerformAction), null, 0, 15000);
和
在新线程中使用System.Timers.Timer?
Thread thread = new Thread(new ThreadStart(PerformActionWithTimer));
thread.Start();
void PerformActionWithTimer()
{
//Timer inside this
}
答案 0 :(得分:2)
没有System.Windows.Timer
这样的东西。大概你的意思是System.Windows.Forms.Timer
。不要尝试在多线程场景中使用该类。它在UI线程上引发了它的Tick
事件,就是这样。如果您希望计时器在辅助线程上引发事件,请使用System.Timers.Timer
。没有真正的理由直接使用System.Threading.Timer
。
答案 1 :(得分:2)
我强烈建议您不使用System.Timers.Timer
,这主要是由于MSDN documentation中“备注”部分提供的一些信息。
Timer组件捕获并抑制事件处理程序为Elapsed事件抛出的所有异常。
这意味着如果你的计时器已经过去的事件引发了一个你没有明确捕获的异常,那么异常将被吞噬,你永远不会知道发生了什么不好的事。
考虑这个Elapsed
事件处理程序:
static void MyTimer_Elapsed(object sender, System.Timers.ElapsedEventArgs e)
{
Console.WriteLine("Badness! Throwing exception");
throw new ApplicationException("something bad happened");
}
显然,这里的意图是立即终止程序,因为它遇到了不可恢复的错误。但异常永远不会逃到主程序。 .NET中的计时器处理程序基本上是这样的:
try
{
MyTimer_Elapsed(sender, args);
}
catch
{
// Why would anybody want to know that something bad happened?
}
这是一个隐藏的错误,因此我不会使用它。
此外,无法指定将在事件参数中提供的上下文对象,例如Windows窗体计时器(Tag
属性)或System.Threading.Timer
(传递给构造函数的state
参数)。
System.Timers.Timer
是围绕System.Threading.Timer
的破坏且有限的组件包装器。它的两个便利点(组件包装器和SynchronizingObject
)远远超过了它的愚蠢异常吞咽和缺少用户上下文对象。不要使用它。请改用System.Threading.Timer
。
答案 2 :(得分:1)
这取决于。 System.Timers.Timer
有两种操作模式。
如果SynchronizingObject
设置为ISynchronizeInvoke
实例,则Elapsed
事件将在托管同步对象的线程上执行。通常,这些ISynchronizeInvoke
实例都是我们熟悉的普通旧Control
和Form
实例。因此,在这种情况下,在UI线程上调用Elapsed
事件,它的行为类似于System.Windows.Forms.Timer
。否则,它实际上取决于所使用的特定ISynchronizeInvoke
实例。
如果SynchronizingObject
为null,则在Elapsed
线程上调用ThreadPool
事件,其行为类似于System.Threading.Timer
。事实上,它实际上在幕后使用了System.Threading.Timer
,并在收到定时器回调后进行编组操作。
在您的特定情况下,您创建的System.Timers.Timer
没有分配同步对象,因此它的行为与System.Threading.Timer
相同。