Основные вопросы о синтаксисе свойства Objective-C - PullRequest
4 голосов
/ 11 марта 2010

У меня есть несколько основных вопросов относительно синтаксиса и использования свойств в Цели C:

Предположим, следующее объявление в заголовке:

@interface TestObject : NSObject {

    NSArray *myArray;
}

@property (nonatomic, retain) NSArray *myArray;

В реализации, могу ли я:

  1. Элемент списка
  2. Используйте myArray и self.myArray взаимозаменяемо для установки и получения целей?
  3. * self.myArray = nil эквивалентно [myArray release]?
    Если да, то есть ли причина использовать self.myArray = nil вместо [myArray release]?

Ответы [ 3 ]

5 голосов
/ 11 марта 2010
  1. myArray и self.myArray на самом деле разные. myArray напрямую обращается к переменной, тогда как self.myArray (что эквивалентно [self myArray]) вызывает метод доступа. Большинство людей согласны с тем, что вы должны использовать self.myArray (или [self myArray]) все время и никогда не использовать myArray напрямую. Это потому, что средство доступа может иметь побочные эффекты; например, KVO не будет работать, если вы установите свою переменную напрямую, и управление памятью не будет для вас обработано.

  2. Ваша собственность объявлена ​​с retain, поэтому self.myArray = anArray (то же самое, что и [self setMyArray:anArray]) выполняет следующее:

    1. Сохраните anArray, который скоро станет новым myArray.
    2. Отпустите старый myArray, который скоро перестанет быть myArray.
    3. Измените указатель myArray, чтобы он теперь указывал на anArray.

Поэтому, когда вы делаете self.myArray = nil, один из шагов (# 2) действительно освобождает старый массив. (А поскольку новый - nil, нам не нужно беспокоиться о его управлении памятью, даже если мы сохранили его.) Так что да, self.myArray = nil - верный способ выпуска myArray.

ОДНАКО, если вы говорите о выпуске myArray в dealloc, обычно стоит использовать [myArray release], потому что вызов self.myArray = nil будет иметь побочные эффекты, если какие-либо другие объекты наблюдают за myArray через КВО. Так что, хотя соответствует стандартам управления памятью, не хорошая идея написать метод dealloc с использованием self.myArray = nil.

4 голосов
/ 11 марта 2010

Оба существующих ответа неверны.

@ synthesize генерирует сеттеры и геттеры, которые выглядят так:

- (void)setMyArray:(NSArray*)array {
    if( myArray != array ) {
        [myArray release];
        myArray = [array retain];
    }
}

- (NSArray*)myArray {
    return myArray;
}

(Обратите внимание, что они не совсем такие, и отличаются, если вы указываете копию или другие атрибуты, но это основная формула). Теперь мы можем видеть, что self.myArray = nil; освободит старый массив. self.myArray и myArray не являются взаимозаменяемыми для настройки. Более того, self.myArray = nil; продолжит работать в мире, где собирается мусор.

Как указывает Дейв Делонг, self.myArray = nil уведомит любого, кто наблюдает за myArray, об измененном значении, что может быть проблемой, если вы сделаете это в своем методе dealloc. Чтобы избежать этого случая, ваш dealloc будет выглядеть примерно так:

- (void)dealloc {
    [myArray release]; myArray = nil;
    [super dealloc];
}

(примечание myArray = nil; - это стилистический выбор здесь.)

0 голосов
/ 11 марта 2010

Чтобы настроить сеттеры / геттеры, вы должны реализовать их в основном как:

+ (NSArray*) myArray {
return myArray;
}

+ (void) setMyArray:(NSArray*)input{
myArray = input;
}
Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...