OC - runtime常见用法小结

消息机制 - 调用私有方法

OC的runtime特性,使其没有严格意义上的私有方法。

objc_getClass()
sel_registerName()
objc_msgSend()

例:
@interface MyObjcet : NSObject
@end

@implementation MyObjcet
- (void)myFunction
{
    NSLog(@"myFunction");
}
@end

//即使myFunction方法没有通过.h暴露出来,也是可以调用成功的。
MyObjcet *obj = [MyObjcet new];
objc_msgSend(obj, sel_registerName("myFunction"));

方法交换

很多时候,我们想要对系统框架的某些方法添加一些自定义逻辑。继承是个解决办法,但得改代码,如何尽可能少的侵入项目呢?

class_getClassMethod()
class_getInstanceMethod()
method_exchangeImplementations()

例: NSMutableDictionary的setObject:forKey:方法,当obj为nil的时候就会抛异常。多写几个if其实也ok,可是...
+ (void)load
{
  Class clas = [object_getClass([NSMutableDictionary dictionary]) class];
  Method original = class_getInstanceMethod(clas, @selector(setObject:forKey:));
  Method new = class_getInstanceMethod(clas, @selector(he_setObject:forKey:));
  method_exchangeImplementations(original, new);
}

@implementation NSMutableDictionary (HECrashHandle)
- (void)he_setObject:(id)anObject forKey:(id)aKey{
    if(aKey == nil) return;
    if(anObject == nil){
        [self removeObjectForKey:aKey];
    }else{
        [self he_setObject:anObject forKey:aKey];
    }
}
@end


分类中添加属性

分类的初衷是为扩展方法而存在的,但很多时候我们需要在分类中添加属性以满足需求。

objc_setAssociatedObject()
objc_getAssociatedObject()

例: 为UIView添加属性myDesc

@interface UIView (Desc)
@property NSString *myDesc;
@end

@implementation UIView (Desc)
- (NSString *)myDesc
{
    return objc_getAssociatedObject(self, _cmd);
}
- (void)setMyDesc:(NSString *)myDesc
{
    objc_setAssociatedObject(self, @selector(myDesc), myDesc, OBJC_ASSOCIATION_COPY_NONATOMIC);
}
@end

添加方法

这个我这没怎么用上,如果有好的使用场景,欢迎在下方的评论区一起交流

resolveClassMethod:
resolveInstanceMethod:
class_addMethod()

示例:
void myMethodIMP(id self, SEL _cmd) { .... }

@implementation MyClass
+ (BOOL)resolveInstanceMethod:(SEL)aSEL
{
    if (aSEL == @selector(resolveThisMethodDynamically)) {
          class_addMethod([self class], aSEL, (IMP) dynamicMethodIMP, "v@:");
          return YES;
    }
    return [super resolveInstanceMethod:aSEL];
}
@end

你可能感兴趣的:(OC - runtime常见用法小结)