为什么clang允许没有@implementation的@interface?它有什么作用?

时间:2012-06-22 16:48:22

标签: objective-c clang objective-c-category

我有以下类/协议:

@interface Super
@end
@implementation Super
@end
@interface Sub1
@end
@implementation Sub1
@end
@interface Sub2
@end
@implementation Sub2
@end

@protocol FooProtocol
- (void) foo;
@end
@interface Sub1 (FooCategory) <FooProtocol>
@end
@implementation Sub1 (FooCategory)
- (void) foo {}
@end
@interface Sub2 (FooCategory) <FooProtocol>
@end
@implementation Sub2 (FooCategory)
- (void) foo {}
@end
@interface Super (FooCategory) <FooProtocol>
@end
// Notice that there is no @implementation Super (FooCategory)

这允许我编写类似于此的函数:

void callFoo(NSArray *supers) {
  for (Super *theSuper in supers) {
    [theSuper foo];
  }
}

Sub1Sub2只有Super个子类。我基本上想要一个类别方法中的多态。如果我为@interface指定了Super,但未提供@implementation,则clang不会给我任何警告/错误。

这是一个非常糟糕的黑客?

潜在的缺点是什么?

2 个答案:

答案 0 :(得分:2)

(最初来自对zneak答案的评论。)

The Objective-C Programming Language中所述,类别中的方法在运行时真正成为目标类的一部分 - 这就是为什么破坏现有方法可能是危险的,以及为什么实现相同类别的多个类别的行为方法未定义。一旦安装了该方法,它与最初的方法没有什么不同:

  

类别方法可以执行本类中定义的方法可以执行的任何操作。在运行时,没有区别。类添加到类中的方法由所有类的子类继承,就像其他方法一样。

可以在Super上创建一个类别,并在其子类上实现相同方法的类别,并且它们的工作方式与它们本身的一部分完全相同。 (虽然我建议遵循zneak关于在Super上实现存根方法的建议,以帮助调试它是否会被意外调用。)

答案 1 :(得分:1)

Objective-C没有“抽象方法”的概念。当你需要一个时,你几乎必须选择,但要使用一些黑客。

虽然我建议你把方法放在Super中,如果被调用则抛出异常。