2012-06-12 169 views
0

我有一个基类,它具有用于返回构建服务url的各种信息的类定义的类方法。基类还有一个为构建该URL而定义的实例方法。我希望基类有这个方法的默认实现,所以当我需要url不同时,我只需要在我的子类中重写它。我如何让这个基方法调用重写的类方法来使用子类中的类方法构建url?下面是我现在已经不工作代码:在超类的子类中重写的调用方法

基类方法:

- (NSString *)buildRequestUrlString{ 
    return [Utils serviceEndpointForOperationId:[[self class]operationId] version:[[self class] operationVersion] andRequestMethod:[[self class] methodType]; 
} 

operationId,operationVersion和methodType是在子类中实现类的方法,但是当子使以下调用:

[super buildRequestUrlString]; 

它使用从基类的类的方法来建立我的终点,而不是类的方法在我的子类。我如何让它不这样做?它甚至有可能吗?

由于提前,

尼克

回答

0

我会为此使用模板模式。基本上在您的基类中创建3个实例方法,以便在基类中获得您的operationId等,它们只返回nil。然后在你的子类中重写这3个方法来返回正确的值。

你buildRequestUrlString方法使用[自operationId]等

+0

这正是我所做的,除非它们不是实例方法,它们是类方法。如果它们是实例方法,这将会起作用,但我不能使用实例方法,因为我在其他地方使用这些方法来处理其他事情,实例方法在这些情况下不起作用。 –

+0

回过头看这个之后,我意识到我忘记了重写三个类的方法。这就是为什么它默认这三种方法的基础实施。感谢您所有的帮助。 –

1

使用self,而不是super

[self buildRequestUrlString]; 

(或解释为什么你的情况不起作用)。

回应的评论,这听起来像你的类分解是不正确的(或你感到困惑)。具体来说,这可能就是为什么你收到三个答案,都是“使用self”;我们不明白问题出在哪里。

如果您的基类需要从子类调用实例方法,那么它需要对子类实例的引用。即说你有:

@interface Concrete:Base 

然后,基地有可能实现的一个类的方法,如:

+ baseWithConcreteQuantity:(int)aQuant 
{ 
    return [[self alloc] initWithConcreteQuantity:aQuant]; 
} 

它想使用:在Objective-

[Concrete baseWithConcreteQuantity:10]; 

也就是说,类方法C - 与其他语言中的静态方法不同 - 像实例方法一样被继承。

现在,就实例方法而言,您总是从该方法调用super的特定方法的实现。使用super来调用不同的基类的方法非常多从来没有完成,并且确实表明其他事情是错误的。

同样,基类不应该试图专门调用基类中不存在的子类中的功能。

I.e.

// in base 
... 
[self doSomething]; 
... 

- (void)doSomething { ; } 

// where a subclass might 
- (void)doSomething { ... ; [super doSomething]; } 
+0

这是行不通的,因为这会再是一个递归调用。我想要发生的是在超类中定义此方法的默认行为。当在子类上实际调用该方法时,由于子类没有定义buildRequestUrlString,因此它将使用此方法的超类缺省实现。但是在超类的默认实现中,我希望它使用子类的覆盖版本的类方法operationId,opeartionVersion和methodType。 –

0

在你的“buildRequestUrlString” - 方法您的[自类]显然型“基础类”的。

对象继承指南强烈反对尝试访问父类的子类属性,因为父类无论是否存在子类都不知道(也应该知道)。

猜,我不打字不够快,解决这一做说的bbum;)

编辑:This'd是一个黑客,以及对我刚才说的,但你可以交出类-name作为参数:

- (NSString *)buildRequestUrlString:(Class)theClass{ 
    if (!theClass) theClass = [self class]; 
    return [Utils serviceEndpointForOperationId:[theClass operationId] version:[theClass operationVersion] andRequestMethod:[theClass methodType]]; 
} 

[super buildRequestUrlString:[self class]]; 
+0

bbum的答案不是我正在寻找的,所以不要感觉不好:)我想在子类中调用的方法在超类中定义。我只想让超类使用这些方法的重写版本。我试图完成的背后的全部想法是不要一遍又一遍地为每个需要使用此方法的默认实现的子类重复相同的代码。这在C#中很容易完成,并且可以直接使用。 –

+0

我认为这是一个解决方案,但我同意,这将是一个破解。有什么方法可以确定实际执行方法的类的类型吗?如果我能做到这一点,我可以做这件事。 –

+0

好吧,如果你在任何方法中运行[self Class],你会得到当前类的这个方法运行...我可能会误解你,如果对于显而易见的答案如此抱歉... – Bersaelor

相关问题