“CA2000在丢失范围之前处理对象”原因不明

时间:2013-06-19 22:09:06

标签: c# .net static-analysis fxcop

我已经查看了MSDN文档,并采用了此代码片段中推荐的模式:

  BitmapSymbols temp = null;
  try {
    using (var source = bitmaps.Symbols) {
      temp = new BitmapSymbols(source, sizeSymbols);
    }
    _bitmapSymbols = temp;
    temp           = null;
  } finally { 
    if (temp!=null) temp.Dispose(); 
  }

有谁知道为什么在这个例子中报告了temp?我看不到任何执行路径,temp没有被处理,也没有设置为'null'。提前感谢您的任何帮助。

如果我在使用中将作业从 - 并且转移到temp,则会从FxCop生成相同的警告。

BitmapSymbols实现IDisposable,并且是多个位图集合的包装器,可确保它们全部同时处理。

更新
问题提出如下:

  

无论如何,我不明白为什么你想出这个代码而不是简单地使用:
  _bitmapSymbols = new BitmapSymbols(source, sizeSymbols);

原因是如果发生异常,不遵循该模式可能会导致内存泄漏。我正在编写一款游戏,用户可能会在没有重新启动的情况下运行数小时或数天,因此避免内存泄漏对于稳定性非常重要。

2 个答案:

答案 0 :(得分:2)

我终于偶然发现了误报的原因(两个单独的案例),即使在MSDN文档here中建议的模式 CA2000在丢失范围之前处理对象 < / strong>紧随其后:

  1. 如果临时一次性变量的名称不是所示的确切模式,即 camelCase 前面的字符串“temp”到目的地一次性,将生成误报从无法识别推荐的模式。通过更改名称可以轻松消除误报。

  2. 如果目标一次性变量是属性而不是字段或本地,则无法识别该模式。消除误报需要编写一次性使用函数,如下所示:

    void SomeMethod() {
      // :  
      HexgridPath   = SetGraphicsPath();
      // :
    }
    
    GraphicsPath SetGraphicsPath() {
      GraphicsPath path     = null;
      GraphicsPath tempPath = null;
      try {
        tempPath  = new GraphicsPath();
        tempPath.AddLines(new Point[] {
          new Point(GridSize.Width*1/3,                0), 
          new Point(GridSize.Width*3/3,                0),
          new Point(GridSize.Width*4/3,GridSize.Height/2),
          new Point(GridSize.Width*3/3,GridSize.Height  ),
          new Point(GridSize.Width*1/3,GridSize.Height  ),
          new Point(                 0,GridSize.Height/2),
          new Point(GridSize.Width*1/3,                0)
        } );
        path     = tempPath;
        tempPath = null;
      } finally { if(tempPath!=null) tempPath.Dispose(); }
      return path;
    }
    
  3. 第一种情况看起来像是典型的“初级程序员首次分配 - 刚刚离开学校”的错误;

    第二种情况可能更难解决,但很烦人。

    希望遇到这些误报的其他人可以从这种分析中受益。从长远来看,小代码更改比简单地禁用错误更好,以防初级程序员在线下“优化”补救措施。

答案 1 :(得分:0)

我相信删除if (temp != null)会使警告消失。 FxCop不够聪明,无法检查我认为的条件执行路径。

无论如何,我不明白为什么你想出这个代码而不是简单地使用_bitmapSymbols = new BitmapSymbols(source, sizeSymbols);