我将创建一个基类,为所有子类实现非常相似的函数。这是在different question中回答的。但我现在需要知道的是,是否/如何构建各种函数(在基类中)以返回子类对象。这既适用于给定的函数,也适用于函数调用。
(顺便说一句,我正在使用CoreData)
作为基类中的函数(这是来自将成为我的子类的类)
+(Structure *)fetchStructureByID:(NSNumber *)structureID inContext:(NSManagedObjectContext *)managedObjectContext {...}
作为给定函数中的函数调用:
Structure *newStructure = [Structure fetchStructureByID:[currentDictionary objectForKey:@"myId"]];
inContext:managedObjectContext];
结构是我的子类之一,所以我需要重写这两个,以便它们是“通用的”,并且可以应用于其他子类(无论谁调用该函数)。
我该怎么做?
更新:我刚刚意识到在第二部分实际上有两个问题。您无法将[Structure fetch ...]更改为[self fetch ...],因为它是一个类方法,而不是实例方法。我如何解决这个问题?
答案 0 :(得分:2)
如果我理解你的问题,我相信关键是[自我类]成语。
就您的更新请求在当前类上调用类方法的方法而言,您可以使用[self class]
。如:
Structure *newStructure = [[self class] fetchStructureByID:[currentDictionary
objectForKey:@"myId"]];
inContext:managedObjectContext];
编辑:我根据@ rpetrich的评论重新设置此返回id
- 只要您确定要调用的实例的类型,就可以更加清晰并避免使用-isKindOfClass:
-createConfiguredObject
on。
至于第一部分,你可以只返回一个id
(指向任何对象的指针)并记录它将返回它所调用的同一个类的实例。然后在代码中,您需要在方法中实例化新对象的任何地方使用[self class]。
e.g。如果你有一个-createConfiguredObject
方法,它返回一个被调用的同一个类的实例,它将按如下方式实现:
// Returns an instance of the same class as the instance it was called on.
// This is true even if the method was declared in a base class.
-(id) createConfiguredObject {
Structure *newObject = [[[self class] alloc] init];
// When this method is called on a subclass newObject is actually
// an instance of that subclass
// Configure newObject
return newObject;
}
然后您可以在代码中使用它,如下所示:
StructureSubclass *subclass = [[[StructureSubclass alloc] init] autorelease];
subclass.name = @"subclass";
// No need to cast or use isKindOfClass: here because returned object is of type id
// and documented to return instance of the same type.
StructureSubclass *configuredSubclass = [[subclass createConfiguredObject] autorelease];
configuredSubclass.name = @"configuredSubclass";
作为参考,我用-isKindOfClass:
引用并转换为正确的子类如下:
Structure *structure;
// Do stuff
// I believe structure is now pointing to an object of type StructureSubclass
// and I want to call a method only present on StructureSubclass.
if ([structure isKindOfClass:[StrucutreSubclass class]]) {
// It is indeed of type StructureSubclass (or a subclass of same)
// so cast the pointer to StructureSubclass *
StructureSubclass *subclass = (StructureSubclass *)structure;
// the name property is only available on StructureSubclass.
subclass.name = @"myname";
} else {
NSLog(@"structure was not an instance of StructureSubclass when it was expected it would be.");
// Handle error
}