Есть ли разница между" переменной экземпляра "и" свойством " в Objective-c?
есть ли разница между" переменной экземпляра "и" свойством " в Objective-c?
Я не очень уверен в этом. Я думаю, что" свойство " - это переменная экземпляра, которая имеет методы доступа, но я могу ошибаться.
5 ответов:
свойство-это более абстрактное понятие. Переменная экземпляра-это буквально просто слот для хранения, как слот в структуре. Обычно другие объекты никогда не должны обращаться к ним напрямую. Свойство, с другой стороны, является атрибутом вашего объекта, к которому можно получить доступ (это звучит неопределенно, и это должно быть). Обычно свойство возвращает или задает переменную экземпляра, но оно может использовать данные из нескольких или вообще не использовать. Например:
@interface Person : NSObject { NSString *name; } @property(copy) NSString *name; @property(copy) NSString *firstName; @property(copy) NSString *lastName; @end @implementation Person @synthesize name; - (NSString *)firstName { [[name componentsSeparatedByString:@" "] objectAtIndex:0]; } - (NSString *)lastName { [[name componentsSeparatedByString:@" "] lastObject]; } - (NSString *)setFirstName:(NSString *)newName { NSArray *nameArray = [name componentsSeparatedByString:@" "]; NSArray *newNameArray [[NSArray arrayWithObjects:newName, nil] arrayByAddingObjectsFromArray:[nameArray subarrayWithRange:NSMakeRange(1, [nameArray size]-1)]]; self.name = [newNameArray componentsJoinedByString:@" "]; } - (NSString *)setLastName:(NSString *)newName { NSArray *nameArray = [name componentsSeparatedByString:@" "]; NSArray *newNameArray [[nameArray subarrayWithRange:NSMakeRange(0, [nameArray size]-2)] arrayByAddingObjectsFromArray:[NSArray arrayWithObjects:newName, nil]]; self.name = [newNameArray componentsJoinedByString:@" "]; } @end
(Примечание: приведенный выше код багги в том, что он предполагает, что имя уже существует и имеет по крайней мере два компонента (например, "Билл Гейтс", а не просто "Гейтс"). Я чувствовал, что исправление этих предположений сделает фактическую точку кода менее ясной, поэтому я просто указываю на нее здесь, чтобы никто не повторил эти ошибки невинно.)
свойство-это удобный способ реализации геттера / сеттера для некоторого значения с дополнительными полезными функциями и синтаксисом. Свойство может быть поддержано переменной экземпляра, но вы также можете определить getter/setter, чтобы сделать что-то более динамичное, например, вы можете определить свойство нижнего регистра в строке, которая динамически создает результат, а не возвращает значение некоторой переменной-члена.
вот пример:
// === In your .h === @interface MyObject { NSString *propertyName; } // ... @property (nonatomic, retain) NSString *propertyName; // === In your .m @implementation === @synthesize propertyName /* = otherVarName */;
The
@property
линия определяет свойство с именемpropertyName
типаNSString *
. Это можно получить/установить, используя следующий синтаксис:myObject.propertyName = @"Hello World!"; NSLog("Value: %@", myObject.propertyName);
когда вы назначаете или читаете из
myObject.propertyName
вы действительно вызываете методы setter / getter на объекте.The
@synthesize
строка сообщает компилятору сгенерировать эти геттеры / сеттеры для вас, используя переменную-член с тем же именем свойства для хранения значения (илиotherVarName
если вы используете синтаксис в комментариях).вместе с
@synthesize
вы все еще можете переопределить один из геттеров/сеттеров, определив свой собственный. Соглашение об именовании для этих методов являетсяsetPropertyName:
для сеттера иpropertyName
(илиgetPropertyName
, не стандартный) для геттера. Другой все равно будет создан для вас.в своем
@property
строка вы можете определить ряд атрибутов в parens для свойства, которое может автоматизировать такие вещи, как потокобезопасность и управление памятью. По умолчанию свойство является атомарным, что означает, что компилятор обернет@synthesiz
ed get / set звонки с соответствующими блокировками для предотвращения проблем параллелизма. Вы можете указатьnonatomic
атрибут, чтобы отключить это (например, на iPhone вы хотите по умолчанию большинство свойствnonatomic
).есть 3 значения атрибутов, которые управляют управлением памятью для любого
@synthesized
сеттеры. Первый - этоretain
который будет автоматически отправлятьrelease
к старым значениям свойства, иretain
к новым ценностям. Это очень полезно.второй -
copy
что будет делать копию любых переданных значений, а не сохранять их. Это хорошая практика, чтобы использоватьcopy
для NSString, потому что вызывающий может передать в NSMutableString и изменить его из-под вас.copy
сделает новую копию ввода, к которому только у вас есть доступ.третий
assign
который назначает прямой указатель без вызова метода retain / release для старого или нового объекта.наконец, вы также можете использовать
readonly
атрибут для отключения сеттер для свойства.
Я использую свойства интерфейса - где объект взаимодействует с другими объектами и переменные экземпляра-это то, что вам нужно внутри вашего класса - никто, кроме вас, не должен видеть и манипулировать ими.
по умолчанию свойство readwrite будет поддерживаться переменной экземпляра, которая снова будет автоматически синтезирована компилятором.
переменная экземпляра-это переменная, которая существует и сохраняет свое значение для жизни объекта. Память, используемая для переменных экземпляра, выделяется при первом создании объекта (через alloc) и освобождается при освобождении объекта.
Если не указано иное, синтезированная переменная экземпляра имеет то же самое имя как свойство, но с префиксом подчеркивания. Например, для свойства firstName синтезированная переменная экземпляра будет называться _firstName.
ранее люди использовали свойства публично и ivars для частного использования, но с тех пор, как несколько лет назад, вы также можете определить свойства в
, в последних кодах от Apple, ivars больше не используются. Я думаю, потому что это больше похоже@implementation
для использования их в частном порядке. Но я бы все равно использовал ivars, когда это возможно, так как есть меньше букв для ввода, и он работает быстрее в соответствии с в этой статье. Это имеет смысл, поскольку свойства должны быть "тяжелыми": они должны быть доступны либо из сгенерированных геттеров/сеттеров, либо из тех, которые написаны вручную.objc
, а неC/C++
, плюс это проще использовать свойства сassign
,nullable
и т. д.