background image

C++

 

 编译器无法捕捉到的

 

     8

      种错误

 

 

C++是一种复杂的

编程

语言,其中充满了各种微妙的陷阱。在 C++中几乎有

数不清的方式能把事情搞砸。幸运的是,如今的编译器已经足够智能化了,能
够检测出相当多的这类编程陷阱并通过编译错误或编译警告来通知程序员。最
终,如果处理得当的话,任何编译器能检查到的错误都不会是什么大问题,
因为它们在编译时会被捕捉到,并在程序真正运行前得到解决。最坏的情况下,
一个编译器能够捕获到的错误只会造成程序员一些时间上的损失,因为他们
会寻找解决编译错误的方法并修正。

那些编译器无法捕获到的错误才是最危险的。这类错误不太容易察觉到,但可
能会导致严重的后果,比如不正确的输出、数据被破坏以及程序崩溃。随着项
目的膨胀,代码逻辑的复杂度以及众多的执行路径会掩盖住这些 bug,导致
这些 bug 只是间歇性的出现,因此使得这类 bug 难以跟踪和调试。尽管本文
的这份列表对于有经验的程序员来说大部分都只是回顾,但这类 bug 产生的
后果往往根据项目的规模和商业性质有不同程度的增强效果。

这些示例全部都在 Visual Studio 2005 Express 上测试过,使用的是默认告
警级别。根据你选择的编译器,你得到的结果可能会有所不同。我强烈建议所
有的程序员朋友都采用最高等级的告警级别!有一些编译提示在默认告警
级别下可能不会被标注为一个潜在的问题,而在最高等级的告警级别下就会
被捕捉到!(注:本文是这个系列文章的第 1 部分)

1)变量未初始化

变量未初始化是 C++编程中最为常见和易犯的错误之一。在 C++中,为变量

所分配的内存空间并不是完全 干净的 ,也不会在分配空间时自动做清零处
理。其结果就是,一个未初始化的变量将包含某个值,但没办法准确地知道这
个值是多少。此外,每次执行这个程序的时候,该变量的值可能都会发生改变。
这就有可能产生间歇性发作的问题,是特别难以追踪的。看看如下的代码片段:

1
2
3
4

if (bValue) 
     // do A 
else
     // do B

如果 bValue 是未经初始化的变量,那么 if 语句的判断结果就无法确定,两个
分支都可能会执行。在一般情况下,编译器会对未初始化的变量给予提示。下
面的代码片段在大多数编译器上都会引发一个警告信息。

1
2
3
4

int foo() 

    int nX; 
    return nX;