自动释放,功能完成时释放对象

时间:2011-04-04 18:01:25

标签: iphone memory-management

- (BOOL)textFieldShouldEndEditing:(UITextField *)textField
{ 
   static NSCharacterSet *charSet = nil;
    if (!charSet) {
        charSet = [[[NSCharacterSet characterSetWithCharactersInString:@"0123456789."] invertedSet] retain];
    }
    NSRange loc = [(NSString*)textField.text rangeOfCharacterFromSet:charSet];
    if (loc.location != NSNotFound) {
        UIAlertView *errorAlert = [[UIAlertView alloc] initWithTitle:NSLocalizedString(@"error!",@"")
                                                             message:@"description."
                                                            delegate:self
                                                   cancelButtonTitle:NSLocalizedString(@"OK",@"")
                                                   otherButtonTitles:nil];
        [errorAlert show];
        [errorAlert release];
        return NO;

    }
    return YES;
}

我有一个与autorelease相关的问题。

我知道当我以这种方式创建对象时:

 charset =[[NSCharacterSet characterSetWithCharactersInString:@"0123456789."] invertedSet];

对象是自动释放的。

我有疑问 - 为什么在这个对象上有 retain 的原因是 - 在首次调用函数后释放对象?

1 个答案:

答案 0 :(得分:2)

这是因为charSet被声明为静态。正常范围规则适用,因此它仅在此方法中可见。但是,静态变量不会存在于堆栈中,并在方法返回时保留它们的值,因此如果再次调用它们仍然具有相同的值。这就是为什么有“if(!charSet)” - 这会检查对象是否已经创建,所以如果是这样可以重新使用现有对象。

没有-retain,NSCharacterSet对象是自动释放的,并且它所居住的内存块可以(并且将)用于其他内容。但是当发生这种情况时,指向该内存的charSet*指针不会重置为nil。它仍然具有旧的价值;由于该值为非零,因此if(!charSet)为false,因此不会创建新对象。但是,由于旧对象被破坏,所以没有人知道该指针引用的内存可能是什么 - 它可能是随机垃圾,它可能是其他一些对象,它可能是任何东西。