【发布时间】:2014-10-30 01:09:13
【问题描述】:
我正在使用“Microsoft Minimal Rules”代码分析集构建我的项目,它在此方法上为我提供了 CA2000:
private Timer InitializeTimer(double intervalInSeconds)
{
Timer timer = null;
try
{
timer = new Timer { Interval = intervalInSeconds * 1000, Enabled = true };
timer.Elapsed += timer_Elapsed;
timer.Start();
}
catch
{
if (timer != null)
{
timer.Dispose();
}
}
return timer;
}
这个方法只是从一个以秒为单位的时间间隔创建一个新的System.Timers.Timer。我有三个这样的计时器正在运行(每秒一个,每分钟一个和每半小时一个)。也许最好有一个计时器并检查经过的事件处理程序是否已经过了一分钟或半小时,但我不知道,这在这个时候更容易,它是继承的代码,我不想破坏一切还没有。
这个方法让我臭名昭著
Warning 21 CA2000 : Microsoft.Reliability : In method 'TimerManager.InitializeTimer(double)', call System.IDisposable.Dispose on object '<>g__initLocal0' before all references to it are out of scope.
现在我正在调用 Dispose 并认为这就足够了?我还在类自己的 IDisposable 实现中处理所有计时器。
我在这里错过了什么?
【问题讨论】:
-
取出对象初始化器语法 - 这就是触发警告的原因(因为对象存在,构造,但在初始化器运行时未分配给
timer。我试图找到欺骗问题处理这个。 -
好吧,不要为了愚蠢的工具而抛弃初始化语法。警告是虚假的,在调用 Start() 之前没有什么可处理的。吞下异常并返回一个已处理的对象,现在 那 将是值得抱怨的事情。
-
@HansPassant - 由于
Interval可以抛出ArgumentException,因此分析正确的是,此一次性对象将在没有调用Dispose的情况下泄漏。没有任何记录(我可以找到)说如果Start没有被调用,你不需要Dispose计时器(尽管这可能适用于当前的实现)。 -
如果记录在案,我们就不会拥有这个网站。有时我们不得不使用你自己的脑袋。
标签: c# .net timer code-analysis