3

我已经把下面的小例子,其中的Xcode(4.5.2)静态分析显然没有检测到泄漏,为了核实一些意见我已经就这个静态分析:Xcode静态分析器不检测泄漏?

#import <Foundation/Foundation.h> 

@interface Foo : NSObject { 
    NSArray *array; 
} 
@property (nonatomic, retain) NSArray *array; 
- (void)bar; 
@end 

@implementation Foo 
@synthesize array; 
- (void)bar 
{ 
    // Shouldn't the static analyzer flag this as a leak? 
    array = [[NSArray alloc] initWithObjects:@"hello", @"world", nil]; 
} 
@end 

int main(int argc, const char *argv[]) 
{ 
    @autoreleasepool { 
     Foo *foo = [[Foo alloc] init]; 

     [foo bar]; 
     [foo bar]; 
     [foo bar]; 

     [foo release]; 
    } 

    return 0; 
} 

如果我没有弄错,重复调用bar将泄漏NSArray个实例。 bar创建一个NSArray实例,其名称暗示它不会有+1保留计数。先前分配给array实例变量的实例泄漏,因为它永远不会释放。

然而,真正令我关心的是,我在某处读到ARC基本上使用与静态分析器相同的算法。这是否意味着这个代码也会在ARC下泄漏?或者,即使没有__strong限定符或相应的(strong)属性,ARC是否默认将所有实例变量视为强壮?

+1

是的,在ARC下,所有实例变量(和范围内的局部变量)都被视为强变量。 – Mario

回答

5

无弧:

它没有检测到泄漏,因为阵列是一个实例variable.So不被认为是泄漏到其分配到具有保留计数到1的对象,这是因为实例变量数组仍然可以访问并且有效。
即使您多次调用该方法,静态分析器也不足以知道该数组指向一个保留变量。
静态分析器只是帮助您知道何时以单一方法泄漏对象。
但试图改变方法方式:

- (void)bar 
{ 
    // Shouldn't the static analyzer flag this as a leak? 
    NSArray* array2 = [[NSArray alloc] initWithObjects:@"hello", @"world", nil]; 
} 

将由静态分析仪进行检测。

关于ARC

弧这个代码没有泄漏,因为当你说阵列=,这就像如果你:

  1. 释放数组:
  2. 保留新创建的对象;
  3. 将其分配给实例变量。

所以我建议转向ARC如果可以的话。

+0

我明白了,谢谢!所以我不能依靠静态分析器来安全地检测我的Cocoa代码中的所有内存泄漏。更不用说核心基金会的东西... – tajmahal

+0

只是为了简单的泄漏;仪器也没有检测到泄漏,但我相信他们会稍后改进,现在我们只需要做一些额外的调试。 –

+1

不幸的是,在最常见的情况下,静态检测所有内存泄漏会减少暂停问题。 –

相关问题