【问题标题】:'ptr = nil' vs '[ptr release]' in Objective-C?Objective-C中的'ptr = nil'与'[ptr release]'?
【发布时间】:2011-10-01 15:38:53
【问题描述】:

我是 Objective-C 的新手,不得不分配和释放内存。我发现有时当我尝试在重新分配指针之前使用[ptr release] 时,我稍后会得到一个SIGABRT,而如果我使用ptr = nil 我不会,但我不确定这是否真的解除分配那个指针指向什么。所以我想确切地知道ptr = nil 的作用,而不是[ptr release]

【问题讨论】:

    标签: objective-c memory pointers


    【解决方案1】:

    这可能是由于对 Cocoa 的内存管理规则缺乏了解,特别是与对象所有权有关的问题。根据您创建对象的方式,您要么拥有它,要么拥有其他东西。是否需要释放对象取决于您是否拥有该对象(您要么保留它,要么使用以allocnewcopymutableCopy 开头的方法创建它) .你可以在Apple's documentation on memory management阅读更多关于规则的详细信息。

    此外,您应该注意有关属性的任何规则。正如sergio 提到的,如果一个属性指定它保留一个对象,它将处理对retainrelease 的调用。因此,例如,如果您使用alloc 分配某些东西,那么您就拥有该对象。如果您随后将其分配给保留该对象的属性,那么您该属性将保留该对象,因此根据您之后所做的事情,您可能还希望释放该对象以放弃所有权对象。

    设置一个指向nil 的简单指针不会释放对象,也不会算作release。因此,根据您创建对象的方式,您应该知道是否需要释放该对象。上面链接的文档包含的示例也可以帮助您加快速度。一个警告:这种东西会随着自动引用计数而发生变化,因为您不会对retainrelease 等进行任何处理,并且编译器会接管大部分工作,但是如果您不使用 ARC,暂时不要担心(但以后再担心)。

    【讨论】:

    • 假设我有一个我保留的类属性:@property (nonatomic, retain) ResultsVC* resultsVC;然后我分配它: self.resultsVC = [[ResultsVC alloc] initWithNibName:@"ResultsVC" bundle:nil];我现在需要释放它两次以避免泄漏吗?
    • 不行,分配给属性后需要释放一次。稍后在您的dealloc 方法中(或其他地方,如果您要释放内存),您需要将该属性设置为nil 以再次释放它。同样,property 保留了它,并且该属性将在其值更改时释放它(nil 或其他对象)。
    【解决方案2】:

    使用:

    [ptr release];
    

    您实际上是在减少 ptrretainCount。如果 ptrretainCount 下降到 0,则 ptr 将被释放,内存也将被释放。

    当您写入ptr = nil; 时,您只是在“重置”ptr 指向的内存地址。

    【讨论】:

    • 而写ptr = nil; 代替[ptr release]; 或在[ptr release]; 之前会导致泄漏。
    • "如果 ptr 的 retainCount 下降到 0,ptr 将被释放,内存也将被释放。" --如果我想重用指针指向别的东西,但不再需要它指向的对象,有没有办法解除分配对象而不是指针?
    • 只需向您的对象发送release 消息,然后重新分配您想要的任何指针变量!
    【解决方案3】:

    ptr = nil 将使您的 ptr 变量具有 nil 值并且不会释放您的指针;所以它在没有 SIGABRT 的情况下工作的原因是对象没有被释放。

    当您分配给retain 属性时,分配nil 也意味着release

    @property(nonatomic, retain) .... ptr;
    .....
    self.ptr = nil;
    

    最好遵循 release 语句并赋值为 nil:

    [ptr release];
    ptr = nil;
    

    这将防止在释放后对释放的对象进行任何不必要的使用(这对于可以在不同方法中使用的类 ivars 很有意义)。

    如果你能提供一些显示 SIGABRT 的代码,就会更容易被发现。

    【讨论】:

      猜你喜欢
      • 2020-04-28
      • 1970-01-01
      • 2016-05-20
      • 1970-01-01
      • 2015-03-24
      • 1970-01-01
      • 2021-06-25
      • 2021-04-06
      相关资源
      最近更新 更多