为什么在没有定义UIWindow * _window的情况下可以访问_window?

时间:2011-11-30 08:21:31

标签: objective-c ios

这是一个后续问题:Why rename synthesized properties in iOS with leading underscores?

MyDelegate.h

中的

#import <UIKit/UIKit.h>

@interface MyAppDelegate

@property (strong, nonatomic) UIWindow *window;
@property (strong, nonatomic) MyMainViewController *mainViewController;

@end
MyDelegate.m

中的

#import "MyAppDelegate.h"

@implementation MyAppDelegate

@synthesize window = _window;
@synthesize mainViewController = _mainViewController;

除了original question中有关_前缀的好处的解释之外,我想知道为什么_window可以访问

@synthesize window = _window;

没有在任何地方定义,在第一次使用之前?

2 个答案:

答案 0 :(得分:3)

这既是声明又是定义。 @synthesize指令能够创建访问器方法和实例变量。来自TOCPL,"Declared Properties: Property Implementation Directives"

  

您可以使用property=ivar形式表示应该为属性使用特定的实例变量...
  对于现代运行时(请参阅Objective-C运行时编程指南中的“Runtime Versions and Platforms”),实例变量根据需要进行合成。如果已存在同名的实例变量,则使用它。< / p>

所以,如果你已经宣布了伊娃,

@interface MyAppDelegate : NSObject
{
    NSWindow * _window;
}

将被使用(这在“遗留”平台中是必需的)。否则,它由@synthesize指令创建。在任何一种情况下,类中的结果都是相同的,尽管应该注意合成变量的创建就好像它们是用@private指令声明的那样;子类可以直接访问属性,但不能访问ivar。对无与伦比的Cocoa With Love进行更多调查:Dynamic ivars: solving a fragile base class problem

答案 1 :(得分:1)

 @synthesize window = _window;

它是在那里定义的。这就是说,你知道我所说的属性被称为window,在背景中,将它变成一个名为_window的ivar,这样如果有人输入

window = blah blah

这会产生编译错误。

这可以防止您直接意外访问ivar,而不是使用合成的访问器。