如何在覆盖某个类别的方法时调用原始实现?

我试图弄清楚事情是如何工作的。 所以我想,当我将覆盖某些方法使用类别,我会得到有趣的NSLogs。

@implementation UIView(Learning) - (UIView *)hitTest:(CGPoint)point withEvent:(UIEvent *)event { NSLog(@"-hitTest:withEvent: event=%@", event); return [self hitTest:point withEvent:event]; } @end 

超级和自我不在这里工作。 有没有办法调用-hitTest:withEvent的原始实现:? 我想要的是NSLog每次-hitTest:withEvent:在UIView上调用。

这只是个人学习的目的。 我希望看到事件的实施。

你可以做,但不能使用一个类别。 一个类别取代了一个方法。 (警告,汽车比喻)如果你有一辆汽车,而你摧毁了那辆汽车,换上一辆新车,你还能用这辆旧汽车吗? 不,因为它已经消失,不再存在。 与类别相同。

你可以做的是使用Objective-C运行时在运行时以不同的名称添加方法(比如“ bogusHitTest:withEvent: ”),然后交换hitTest:withEvent:bogusHitTest:withEvent: 。 这样当代码调用hitTest:withEvent: ,它将执行最初为bogusHitTest:withEvent:写入的bogusHitTest:withEvent: 然后你可以让代码调用bogusHitTest:withEvent:它将执行原始的实现。

所以伪造的方法看起来像:

 - (UIView *) bogusHitTest:(CGPoint)point withEvent:(UIEvent *)event { NSLog(@"executing: %@", NSStringFromSelector(_cmd)); return [self bogusHitTest:point withEvent:event]; } 

交换这些方法的代码将沿着以下方向进行:

 Method bogusHitTest = class_getInstanceMethod([UIView class], @selector(bogusHitTest:withEvent:)); Method hitTest = class_getInstanceMethod([UIView class], @selector(hitTest:withEvent:)); method_exchangeImplementations(bogusHitTest, hitTest); 

你想要做的就是调用方法swizzling: http : //www.cocoadev.com/index.pl? MethodSwizzling

不幸的是,没有办法调用你重写的方法的原始实现。 一旦你在类别中实现它,你已经消除了原来的方法。

发送同样的消息到super应该在你的方法工作; 它将正常调用超类的方法(如果有的话)。

发送相同的消息给self将创build一个无限循环,我相信你已经发现了。