大多数 Cocoa 项目使用下划线作为非IBOutlet
实例变量前缀,并且不使用实例变量前缀IBOutlet
。
我不使用下划线作为IBOutlet
实例变量的原因是,当加载 nib 文件时,如果您有一个用于连接的插座的 setter 方法,则将调用该 setter。 然而,这种机制不使用键值编码,因此不会设置名称以下划线 ( eg _myField
)为前缀的 IBOutlet,除非设置器的名称与插座 ( eg ) 完全相同,这是非标准且粗略的。 set_myField:
另外,请注意,使用类似self.myProp
的属性与访问实例变量不同。当您使用属性时,您正在发送消息,就像您使用括号表示法一样[self myProp]
。所有属性所做的就是为您提供简洁的语法,以便在一行中指定 getter 和 setter,并允许您综合它们的实现;它们实际上并没有使消息分发机制短路。如果你想直接访问一个实例变量但在它前面加上self
你需要把它self
当作一个指针来对待,就像self->myProp
它实际上是一个 C 风格的字段访问一样。
最后,在编写 Cocoa 代码时不要使用匈牙利符号,并避免使用其他前缀,如“f”和“m_”——这会将代码标记为由不“明白”的人编写,并会导致它被其他 Cocoa 开发者怀疑。
一般来说,遵循Apple Developer Connection上的Cocoa 编码指南文档中的建议,其他开发人员将能够获取并理解您的代码,并且您的代码将与所有使用运行时内省的 Cocoa 功能一起工作。
下面是一个窗口控制器类的样子,使用我的约定:
// EmployeeWindowController.h
#import <AppKit/NSWindowController.h>
@interface EmployeeWindowController : NSWindowController {
@private
// model object this window is presenting
Employee *_employee;
// outlets connected to views in the window
IBOutlet NSTextField *nameField;
IBOutlet NSTextField *titleField;
}
- (id)initWithEmployee:(Employee *)employee;
@property(readwrite, retain) Employee *employee;
@end
// EmployeeWindowController.m
#import "EmployeeWindowController.h"
@implementation EmployeeWindowController
@synthesize employee = _employee;
- (id)initWithEmployee:(Employee *)employee {
if (self = [super initWithWindowNibName:@"Employee"]) {
_employee = [employee retain];
}
return self;
}
- (void)dealloc {
[_employee release];
[super dealloc];
}
- (void)windowDidLoad {
// populates the window's controls, not necessary if using bindings
[nameField setStringValue:self.employee.name];
[titleField setStringValue:self.employee.title];
}
@end
您会看到我在我的and方法中使用了Employee
直接引用 an 的实例变量,而我在其他方法中使用了该属性。这通常是一个很好的属性模式:只在初始值设定项、 in以及属性的 getter 和 setter 中触及属性的底层实例变量。-init
-dealloc
-dealloc