Можно ли повторно объявить частные ивары в подклассе, чтобы сделать их доступными?


При подклассе класса Apple, в котором перечислены частные ивары .H file, можно ли повторно объявить эти ивары в вашем собственном подклассе в классе extension @ interface внутри вашего подкласса .файл m для того, чтобы сделать их доступными для реализации вашего подкласса?

2 6

2 ответа:

Необходимо иметь в виду, что объявление переменной экземпляра в подклассе не повторяет объявление существующей переменной экземпляра суперкласса с тем же именем, независимо от предполагаемого повторного объявления в открытом интерфейсе или расширении класса. Даже если вы используете одно и то же имя, это другая переменная экземпляра.

Вы можете попробовать это сами. Например:

@interface Base : NSObject {
@private
    int _number;
}
@end

@implementation Base
- (id)init { self = [super init]; if (self) _number = 10; return self; }
- (void)logNumber { printf("base = %d\n", _number); }
@end

@interface Derived : Base
@end

@interface Derived () {
    int _number;
}
@end

@implementation Derived
- (id)init { self = [super init]; if (self) _number = 20; return self; }
- (void)logNumberDerived { printf("derived = %d\n", _number); }
@end

int main(void) {
    Derived *o = [Derived new];
    [o logNumber];
    [o logNumberDerived];
    return 0;
}

Выходы:

base = 10
derived = 20

Потому что _number в суперклассе отличается от _number в подкласс (расширение). Если вы проверите символы в двоичном выводе с помощью nm -a, Вы заметите, что компилятор генерирует два разных символа:

s _OBJC_IVAR_$_Base._number
s _OBJC_IVAR_$_Derived._number

Я нашел здесь ответ, который точно соответствует моему собственному: http://lists.apple.com/archives/cocoa-dev/2007/Feb/msg00939.html

Если бы они сделали его @ приватным, а не @ защищенным, вам пришлось бы предположить что это неспроста. Эта причина, конечно, может быть просто такова это разумно, чтобы сделать все частным, пока вы не знаете хорошую причину. не...

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

Самое безопасное-это переделать все в своем собственном классе, в то время как обращение к сопровождающему суперкласса с просьбой разоблачить функциональность, необходимая в общедоступном / защищенном интерфейсе.