1.3 使用Xcode静态分析器

近几年来在Xcode开发环境中,编译器技术的最大的改进之一就是引入了Clang静态分析器。Clang静态分析器是一个通过分析源代码来发现常见错误的工具。尽管编译器擅长发现一些错误,但通常会考虑速度而放弃了对一些较难发现的条件的检查。这样一些原本可以发现的错误和一些在代码检查中可以发现的错误,经常会未被发现而成为应用中的bug。未成功释放已分配的内存、死循环、使用未初始化的变量等都是这类错误的例子。普通编译器无法检查到这其中的大部分错误。Clang静态分析器就是为了满足这种需求而专门设计的。

要想在源代码上运行Clang静态分析器,需要选择Build > Build and Analyze。这首先会利用编译器编译代码,然后运行静态分析器。

静态分析器显示检查到的错误的方式和普通的编译警报相似。但是在单击源代码中的一个错误时,你可以获得额外的上下文信息,这些信息采用图形代码流向箭头的形式。这些箭头会指示分析器预测的代码运行时使用的代码路径。这些信息可以帮助你更详尽地了解分析器在发现代码错误时考虑到的具体情况。

看看分析器如何处理常见的编码错误。再次提醒,这里讨论的大部分内容都是后面的章节会详细介绍的高级主题。目前,可以跳过本节,以后在自己的代码中发现这些错误时再回过头来看看这部分。

代码清单1-4显示了一个带有常见错误的示例程序。在本例中,已分配的内存没有被释放。

代码清单1-4 带有内存泄漏的程序

#import <Foundation/Foundation.h>

int main (int argc, const char * argv[])
{
    NSAutoreleasePool * pool = [[NSAutoreleasePool alloc] init];
    NSDate *date = [[NSDate alloc] init];
    NSLog(@"The time is: %@", date);
    [pool drain];
    return 0;
}

在本例中,NSDate对象创建后没有被释放。这段代码的静态分析器输出如图1-13所示。

图1-13 静态分析器输出

注意,该错误在屏幕上方的编译结果面板以及代码中显示。Clang静态分析工具不仅可以捕捉到大多数编译器捕捉不到的错误,同时它的输出也比大多数编译器错误更清晰。如果你展开编译结果中错误消息对应的展开图标,就会显示和该错误相关的两条单独的信息。单击其中的一条消息,会显示内存分配的准确位置以及分析时的程序流程。你可以通过箭头来遍历代码。图1-14显示了错误展开后以及分析器完整输出显示后的相同代码。

图1-14 分析器的详细输出

按照代码清单1-5修改代码后,错误消失并且编译通过。

代码清单1-5 修正后的代码

#import <Foundation/Foundation.h>

int main (int argc, const char * argv[])
{
    NSAutoreleasePool * pool = [[NSAutoreleasePool alloc] init];
    NSDate *date = [[NSDate alloc] init];
    NSLog(@"The time is: %@", date);
    [date release];
    [pool drain];
    return 0;
}

说明

重新编译应用后,Clang静态分析器就不再标记错误了。

目录