Вопросы о переменной экземпляра, свойствах, реализации и интерфейсах - PullRequest
0 голосов
/ 12 июня 2018

Я программирую для платформы iOS последние несколько лет, но в основном использую swift.Однако в последние месяцы передо мной был задан проект, использующий Objective C, и, хотя он мне понравился, и мне было легко его освоить, есть некоторые вопросы, в основном о переменных, которые я до сих пор не совсем понимаю.

1) В чем разница между объявлением переменной экземпляра и свойством?Поскольку компилятор автоматически создает переменную экземпляра для каждого свойства, есть ли реальное преимущество, кроме возможности передавать некоторые параметры, такие как атомарный, неатомарный, сильный, слабый, назначить и т. Д.?

2) В чем разницамежду объявлением переменных в @implementation или свойствами @interface внутри файла .m?Из того, что я понимаю, объявление в @implementation делает его статической переменной, а объявление в @interface делает его переменной экземпляра, это правильно?Кроме того, почему классы, которые наследуются от UIViewController (например), уже имеют @interface в файле .m, а классы, которые наследуют от NSObject, не имеют?

3) (Личный вопрос) Вы обычно устанавливаете свойство как атомарное или неатомарное?Я считаю, что атомарный лучше, потому что, хотя он и медленнее, он безопасен для потоков, но я вижу, что большинство людей используют неатомные.Разница в скорости все еще заметна в настоящее время в зависимости от количества энергии, которое у нас есть?

4) Всякий раз, когда я объявляю две переменные экземпляра с одинаковыми именами в @implementation в двух разных классах, я получаю ошибку «duplicate symbol».Почему это происходит?

Еще один простой вопрос из любопытства: я вижу много вопросов, где в коде @interface есть фигурные скобки, но в моем коде я его никогда не видел, скорее он заканчивается на@ заканчивается как файл @implementation.Было ли это в более ранних версиях Obj-C или есть какая-то реальная разница?

Большое спасибо, я знаю, что это 4 или 5 вопросов, но я так быстро запрыгнул в проект, и я думаю, что мне действительно нужноизучить основы, которые я пропустил, потому что не смог найти ответы на эти вопросы.

Ответы [ 2 ]

0 голосов
/ 12 июня 2018

1) В чем разница между объявлением переменной экземпляра и свойством?Поскольку компилятор автоматически создает переменную экземпляра для каждого свойства, есть ли реальное преимущество, кроме возможности передавать некоторые параметры, такие как атомарный, неатомарный, сильный, слабый, назначить и т. Д.? 1002 *

Свойство можетили может не поддерживаться переменной экземпляра.По умолчанию они есть, но вы можете объявить свойство и явно предоставить как getter, так и setter (если не только для чтения).Тогда у свойства не будет неявно объявленного ivar.Свойства позволяют легко указать, является ли он атомарным или нет, доступен он только для чтения или нет, а также позволяет управлять памятью (сильная, слабая, копировать, назначать).Свойства также обеспечивают поддержку наблюдения значения ключа.

Если вы хотите, чтобы простая переменная использовалась в частном порядке без использования какой-либо из этих функций, то прямой ивар без свойства закончился, поэтому он немного более эффективен.

См. Есть ли разница между "переменной экземпляра" и "свойством" в Objective-c? для получения более подробной информации.

2) В чем разница междуобъявлять переменные в @implementation или в свойствах @interface внутри .m файла?Из того, что я понимаю, объявление в @implementation делает его статической переменной, а объявление в @interface делает его переменной экземпляра, это правильно?Кроме того, почему классы, которые наследуются от UIViewController (например), уже имеют @interface в файле .m, а классы, которые наследуют от NSObject, не имеют?

Закрытый @interface Whatever () в .mизвестен как расширение класса.Это в основном особая безымянная категория.Нет разницы между объявлением ivars там или в блоке @implementation.

Лично я использую расширение класса, чтобы конфиденциально соответствовать протоколам и объявлять частные свойства.Я использую блок @implementation для объявления частных иваров.

Переменные в блоке @implementation являются обычными переменными экземпляра, если они заключены в фигурные скобки.

@implementation {
    // ivars here
}

// variables here are globals. Same as before @implementation or after @end

// methods

@end

Без фигурныхфигурные скобки превращают эти переменные в глобальные.

См. Разница между переменными в интерфейсе Object () {} и @implementation Object @ end и Разница между объявлением переменной в @Implementation And @InterfaceПод .m file для более подробной информации.

3) (Личный вопрос) Вы обычно устанавливаете свойство как атомарное или неатомарное?Я считаю, что атомарный лучше, потому что, хотя он может быть медленнее, он безопасен для потоков, но я вижу, что большинство людей используют неатомные.Разница в скорости все еще заметна в настоящее время с количеством энергии, которое у нас есть?Это просто означает, что присвоение является атомарным, а чтение - атомарным, но это не означает, что потокобезопасен в широком смысле.

См. В чем разница между атомарными и неатомарными атрибутами? для более подробного обсуждения.

4) Всякий раз, когда я объявляю две переменные экземпляра с одинаковымиимя в @implementation в двух разных классах я получаю ошибку "дубликат символа".Почему это происходит?

См. № 2.Вы не должны иметь свои переменные в фигурных скобках @implementation.Поместите переменные туда, где они принадлежат, и проблема исчезнет.

Если вы действительно хотите, чтобы переменная была статической, то поместите ее перед @implementation, чтобы было ясно, что она не является частью классаи префикс объявления переменной с static.Тогда, если у вас два файла с одинаковыми именами в разных файлах, проблем с дублированием не будет, если они статические.

0 голосов
/ 12 июня 2018

1) В чем разница между объявлением переменной экземпляра и свойством?Поскольку компилятор автоматически создает переменную экземпляра для каждого свойства, есть ли реальное преимущество, кроме возможности передавать некоторые параметры, такие как атомарный, неатомарный, сильный, слабый, назначить и т. Д.

Свойства действительнопросто методы, обернутые в синтаксис.Они предназначены для вызова другими классами, при условии, что они предоставляются публично.Переменная экземпляра больше похожа на доступ к полю в C. Вероятно, вам следует использовать свойства по умолчанию (они поддерживают KVO, безопасны для nil и т. Д.).Вы должны по умолчанию использовать свойства для получения / установки, за исключением, возможно, инициализатора.

Обратите внимание, однако, что компилятор не всегда создает переменные экземпляра.Если вы предоставляете как getter, так и setter, вам нужно указать это с помощью @synthesize foo=_foo;.

2) В чем разница между объявлением переменных в @implementation или @interface внутри .mфайл?Из того, что я понимаю, объявление в @implementation делает его статической переменной, а объявление в @interface делает его переменной экземпляра, это правильно?Кроме того, почему классы, которые наследуются от UIViewController (например), уже имеют @interface в файле .m, а классы, наследуемые от NSObject, отсутствуют?

Исторически переменные экземпляра можно было определить только вthe @interface.

3) (Личный вопрос) Вы обычно устанавливаете свойство как атомарное или неатомарное?Я считаю, что атомарный лучше, потому что, хотя он и медленнее, он безопасен для потоков, но я вижу, что большинство людей используют неатомные.Разница в скорости все еще заметна в наше время с количеством энергии, которое у нас есть?

Причина использования nonatomic в том, что atomic на самом деле не решает проблему безопасности потоков так, как вы думаете,Например, это все еще небезопасно для потока, даже если для свойства установлено значение atomic (поскольку значение foo может изменяться между чтением и записью):

self.foo = self.foo + 1;

По этой причине я думаю,наибольшее одобрение nonatomic и обеспечение безопасности ниток, особенно при необходимости.

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...