Вопрос

Если у меня есть что-то вроде UILabel, связанного с файлом xib, нужно ли мне освобождать его при освобождении моего представления?Причина, по которой я спрашиваю, заключается в том, что я не выделяю его, что заставляет меня думать, что мне тоже не нужно его освобождать?например (в заголовке):

IBOutlet UILabel *lblExample;

в процессе реализации:

....
[lblExample setText:@"whatever"];
....

-(void)dealloc{
    [lblExample release];//?????????
}
Это было полезно?

Решение

Если вы будете следовать тому, что сейчас считается наилучшей практикой, вы следует освободите свойства розетки, поскольку вы должны были сохранить их в наборе средств доступа:

@interface MyController : MySuperclass {
    Control *uiElement;
}
@property (nonatomic, retain) IBOutlet Control *uiElement;
@end


@implementation MyController

@synthesize uiElement;

- (void)dealloc {
    [uiElement release];
    [super dealloc];
}
@end

Преимущество этого подхода заключается в том, что он делает семантику управления памятью явной и понятной, и это работает последовательно на всех платформах для всех файлов nib.

Примечание:Следующие комментарии применимы только к iOS до версии 3.0.В версии 3.0 и более поздних версиях вам следует вместо этого просто обнулить значения свойств в viewDidUnload.

Одно из соображений здесь, однако, заключается в том, что ваш контроллер может распоряжаться своим пользовательским интерфейсом и динамически перезагружать его по требованию (например, если у вас есть контроллер представления, который загружает представление из файла nib, но по запросу - скажем, при нехватке памяти - освобождает его, ожидая, что его можно будет перезагрузить, если представление понадобится снова).В этой ситуации вы хотите убедиться, что при удалении основного просмотра вы также отказываетесь от владения любыми другими выходами, чтобы их тоже можно было освободить.Для UIViewController вы можете решить эту проблему, переопределив setView: следующим образом:

- (void)setView:(UIView *)newView {
    if (newView == nil) {
        self.uiElement = nil;
    }
    [super setView:aView];
}

К сожалению, это порождает еще одну проблему.Поскольку UIViewController в настоящее время реализует свой dealloc метод, использующий setView: метод доступа (вместо того, чтобы просто освобождать переменную напрямую), self.anOutlet = nil будет вызван в dealloc а также в ответ на предупреждение памяти...Это приведет к сбою в dealloc.

Решение состоит в том, чтобы убедиться, что переменные выхода также установлены в nil в dealloc:

- (void)dealloc {
    // release outlets and set variables to nil
    [anOutlet release], anOutlet = nil;
    [super dealloc];
}

Другие советы

Я нашел то, что искал, в документах Apple.Короче говоря, вы можете настроить свои объекты как свойства, которые вы освобождаете и сохраняете (или просто @property, @synthesize), но вам не обязательно использовать такие вещи, как UILabels:

http://developer.apple.com/iphone/library/documentation/Cocoa/Conceptual/LoadingResources/CocoaNibs/chapter_3_section_4.html#//apple_ref/doc/uid/10000051i-CH4-SW18

Тот Самый

[anOutlet release], anOutlet = nil;

Часть совершенно излишня, если вы написали setView:правильно.

Если вы не освободите его при освобождении, это увеличит объем памяти.

Смотрите более подробную информацию здесь с графиком распределения объектов инструмента

В некотором смысле вы выделяете метку, создавая ее в IB.

Что делает IB, так это просматривает ваши IBOutlets и то, как они определены.Если у вас есть переменная класса, которой IB должен назначить ссылку на какой-либо объект, IB отправит этому объекту сообщение о сохранении для вас.

Если вы используете properties, IB будет использовать свойство, которое у вас есть, для установки значения, а не для явного сохранения значения.Таким образом, вы обычно помечаете свойства IBOutlet как retain (сохранить):

@property (nonatomic, retain) UILabel *lblExample;

Таким образом, в любом случае (используя свойства или нет) вы должны вызвать release в своем dealloc .

Любой IBOutlet, который является вложенным представлением основного представления вашего Nib, не нужно выпускать, поскольку им будет отправлено сообщение об автоматическом выпуске при создании объекта.Единственные IBOutlet, которые вам нужно выпустить в вашем dealloc, - это объекты верхнего уровня, такие как контроллеры или другие NSObject.Все это упомянуто в документе Apple doc, на который дана ссылка выше.

Если вы устанавливаете IBOutlet не как свойство, а просто как переменную экземпляра, вы все равно должны освободить его.Это связано с тем, что при initWithNib память будет выделена для всех IBOutlets.Таким образом, это один из особых случаев, который вы должны освободить, даже если вы не сохранили или не выделили какую-либо память в коде.

Лицензировано под: CC-BY-SA с атрибуция
Не связан с StackOverflow
scroll top