NSObject init方法的问题

时间:2010-01-03 09:18:08

标签: objective-c cocoa

我对标准NSObject的init()方法有问题。我写了一个类(EFAPersistence),它是NSObject的子类。 EFAPersistance有一个名为 efaDatabase 的属性。

EFAPersistence.h

@interface EFAPersistence : NSObject {
  FMDatabase * efaDatabase;
}

@property (assign) FMDatabase * efaDatabase;

每次创建EFAPersistance实例时,我都希望从我的AppDelegate为efaDatabase分配一个值。

EFAPersistence.m

@implementation EFAPersistence

@synthesize efaDatabase;

- (id)init {
  if (self = [super init]) {
    efaDatabase = [[NSApp delegate] efaDatabase];
  }
  return self;
}

@end

这种分配方式不起作用。但是如果我将代码放在普通方法中,它就可以工作。所以我确信efaDatabase在我的AppDelegate中正确实例化。它只是在我的init()方法中不起作用。这就是为什么我感觉NSApp不在init()方法中工作。

这就是重要的AppDelegate代码的样子。

AppDelegate.h

@interface AppDelegate : NSObject <NSApplicationDelegate> {
  FMDatabase * efaDatabase;
}

AppDelegate.m

- (id)init {
  if (self = [super init]) {
    NSString * databasePath = 
      [[NSBundle mainBundle] pathForResource:@"efa" ofType:@"sqlite"];

    self.efaDatabase = [FMDatabase databaseWithPath:databasePath];

    if (![efaDatabase open]) {
      NSLog(@"Couldn't open database: %@", databasePath);
      // TODO: Create a database here
    }
    self.db = [[EFAPersistence alloc] init];
  }
  return self;
}

正如您所看到的,我正在调用init方法。我也通过使用NSLog()来肯定这一点。调用init()。我试图在EFAPersistence中分配的属性也是在调用init()之前创建的。

总结一切:

如何在init()方法中完成这项工作,这样我就不必在所有的EFAPersistence方法中编写样板代码?

2 个答案:

答案 0 :(得分:4)

我认为当您第一次尝试创建EFAPersistance对象时,您的AppDelegate未设置。这是在AppDelegate.m

的下面一行
self.db = [[EFAPersistence alloc] init];

我想在init完成(返回)之后设置了app委托。

答案 1 :(得分:4)

  

这种分配方式不起作用。但是如果我将代码放在普通方法中,它就可以工作。所以我确信efaDatabase在我的AppDelegate中正确实例化。它只是在我的init()方法中不起作用。这就是为什么我感觉NSApp不在init()方法中工作。

NSApp运行正常。

引用epatel:

  

我想在初始化完成(返回)后设置了app委托。

正确。 nib加载器完全实例化每个对象(包括app委托,如果它在nib中),然后将其设置为它所连接的任何属性的值。这是两个独立的操作;它不会将尚未初始化的对象设置为应用程序委托。

再次引用你(Jens):

  

问题是如何仅在EFAPersistences中分配efaDatabase一次。还有其他方法,如awakeFromNib和viewDidLoad等。但这些方法在普通的NSObject子类中不可用。

不正确的。在初始化对象后,awakeFromNib被发送到 nib中的每个对象。

那就是说,我很好奇为什么你在笔尖中有EFAP​​ersistence。从它的名字来看,它与界面无关。 app委托不应该拥有EFAP​​ersistence,而EFAPersistence不能直接拥有数据库吗?