Objective C合成变量下划线前缀不起作用

时间:2014-07-17 20:30:14

标签: objective-c

我正在阅读官方Apple网站上关于在Apple合成属性的教程。这是一段摘录:

  

除非另行指定,否则合成的实例变量与属性具有相同的名称,但带有下划线前缀。例如,对于名为 firstName 的属性,合成的实例变量将被称为 _firstName

然而,后来,它说:

  

重要说明:如果使用@synthesize而未指定实例变量名称,则如下所示:    @synthesize firstName ;   实例变量将与属性具有相同的名称。   在此示例中,实例变量也将被称为 firstName ,没有下划线。

这些陈述似乎存在分歧。当我使用synthesize synthesize numerator,之后尝试使用_numerator时,会显示以下错误:使用未声明的标识符_枚举器

enter image description here

知道我做错了吗?

2 个答案:

答案 0 :(得分:5)

您可以在@interface中声明实例变量和属性。

在实施中,您可以使用

@synthesize property = instancevariable;

当你这样做时,编译器会创建一个名为" instancevariable"的实例变量。如果它还没有存在,并根据需要为setter和getter生成代码。变量名称是您要使用的任何名称。

@synthesize property;

本身与

相同
@synthesize property = property; 

表示创建的实例变量与该属性具有相同的名称(如果它尚不存在)。是否从下划线开始自己创建实例变量并不重要。该实例变量只是一个实例变量,可能会导致代码严重混淆。

// No synthesize statement

完全相同
@synthesize property = _property;

表示如果实例变量尚未存在,则使用前导下划线创建实例变量。是否自己创建了一个没有下划线的实例变量并不重要。该实例变量只是一个实例变量,可能会导致代码严重混淆。在这种情况下,编译器将发出警告。

有一个例外:如果您自己实现了所有必需的方法(setter和getter,或只是getonly的getter),并且您没有使用@synthesize,那么将不会创建任何实例变量。如果使用@synthesize,将如上所述创建实例变量。

所以最好的选择是宣布@property而不是其他任何东西;将创建以下划线开头的实例变量。如果同时实现setter和getter,或者只实现readonly属性的getter,则可能不需要实例变量。如果需要,可以声明实例变量或使用@synthesize创建它。

答案 1 :(得分:2)

  

如果我不使用合成,并且不为变量声明setter和getter,它们将如何被访问?

Objective-C的最新版本使@synthesize成为属性的默认值,因此您无需显式编写@synthesize firstName; - 编译器将为您处理。

正如@TimReddy在评论中指出的那样,你引用的两个段落之间的区别在于,当你明确使用@synthesize指令时,人们正在谈论行为(ivar与属性的名称相同) ,另一个描述了编译器自动合成ivar时的行为(ivar名称是带有下划线前缀的属性名称)。