iOS-runtime-根据协议名调某一个类有与协议里面放的相同的方法
// // ViewController.m // ObserverTrampoline // // Created by Rob Napier on 9/7/11. // Copyright (c) 2011 __MyCompanyName__. All rights reserved. // #import "ViewController.h" #import "RNObserverManager.h" @protocol MyProtocol <NSObject> @optional - (void)doSomething; - (void)dodo; @end @interface MyClass : NSObject <MyProtocol> @end @implementation MyClass - (void)doSomething { NSLog(@"doSomething :%@", self); } @end @interface MyClass1 : NSObject @end @implementation MyClass1 - (void)dodo1 { NSLog(@"dodo1 :%@", self); } - (void)dodo { NSLog(@"dodo 要走"); } @end @implementation ViewController //@synthesize observerManager=trampoline_; - (void)viewDidLoad { [super viewDidLoad]; //这样就可以执行一些事情,比如一个类遵守某个协议,它可以直接调这个协议执行那个类里面写的something NSSet *observers = [NSSet setWithObjects:[MyClass new],[MyClass1 new], nil]; self.observerManager = [[RNObserverManager alloc] initWithProtocol:@protocol(MyProtocol) observers:observers]; [self.observerManager doSomething]; [self.observerManager dodo]; } @end
实现的方法
#import "RNObserverManager.h" @interface RNObserverManager () @property (nonatomic, readonly, strong) NSMutableSet *observers; @property (nonatomic, readonly, strong) Protocol *protocol; @end @implementation RNObserverManager //协议 集合 - (id)initWithProtocol:(Protocol *)protocol observers:(NSSet *)observers { if ((self = [super init])) { _protocol = protocol; _observers = [NSMutableSet setWithSet:observers]; } return self; } - (void)addObserver:(id)observer { NSAssert([observer conformsToProtocol:self.protocol], @"Observer must conform to protocol."); [self.observers addObject:observer]; } - (void)removeObserver:(id)observer { [self.observers removeObject:observer]; } //NSObject -------- //这个函数让重载方有机会抛出一个函数的签名,再由后面的forwardInvocation:去执行。 - (NSMethodSignature *)methodSignatureForSelector:(SEL)sel { NSMethodSignature * result = [super methodSignatureForSelector:sel]; if (result) { return result; } // Look for a required method struct objc_method_description desc = protocol_getMethodDescription(self.protocol, sel, YES, YES); if (desc.name == NULL) { // Couldn't find it. Maybe it's optional desc = protocol_getMethodDescription(self.protocol, sel, NO, YES); } if (desc.name == NULL) { // Couldn't find it. Raise NSInvalidArgumentException [self doesNotRecognizeSelector:sel]; return nil; } return [NSMethodSignature signatureWithObjCTypes:desc.types]; } //真正执行从methodSignatureForSelector:返回的NSMethodSignature。在这个函数里可以将NSInvocation多次转发到多个对象中,这也是这种方式灵活的地方。(forwardingTargetForSelector只能以Selector的形式转向一个对象) - (void)forwardInvocation:(NSInvocation *)invocation { SEL selector = [invocation selector]; for (id responder in self.observers) { if ([responder respondsToSelector:selector]) { [invocation setTarget:responder]; [invocation invoke]; } } }
参考:http://www.cnblogs.com/biosli/p/NSObject_inherit_2.html