iOS底层原理(二):Runtime研究(二)

这个篇幅我们继续研究Runtime,这里给大家介绍Runtime的API

  • objc_系列函数关注于宏观使用,如类与协议的空间分配,注册,注销等操作

  • class_系列函数关注于类的内部,如实例变量,属性,方法,协议等相关问题

  • objcet_系列函数关注于对象的角度,如实例变量

  • method_系列函数关注于方法内部,如果方法的参数及返回值类型和方法的实现

  • property_系类函数关注与属性*内部,如属性的特性等

  • protocol_系类函数关注与协议相关

  • ivar_xxx函数关注与实例变量的东西

  • sel_xxx主要讨论关于方法编号相关的东西

  • imp_xxx主要讨论关于方法实现相关的

下面我们来玩一下这些常用的api

//交换方法
        Method m1 = class_getInstanceMethod(self, @selector(viewWillAppear:));
        Method m2 = class_getInstanceMethod(self, @selector(tz_viewWillAppear:));        
        method_exchangeImplementations(m1, m2);
// 关联属性
- (void)setViewColor:(NSString *)viewColor{

    objc_setAssociatedObject(self, &associatedObjectKey, @"addProperty", OBJC_ASSOCIATION_RETAIN_NONATOMIC);
}

- (NSString *)viewColor{
    return objc_getAssociatedObject(self, &associatedObjectKey);
}

 /// 创建一类对
    Class TZCat = objc_allocateClassPair([NSObject class], "TZCat", 0);

    /// 添加实例变量
    // const char* types= "v@:"
    NSString* name = @"name";

    class_addIvar(TZCat, name.UTF8String, sizeof(id), log2(sizeof(id)), @encode(id));

    // 添加方法
    class_addMethod(TZCat, @selector(hunting), (IMP)hunting, "v@:");

    /// 注册类
    objc_registerClassPair(TZCat);

    // 创建实例对象
    id cat = [[TZCat alloc] init];
    [cat setValue:@"Tom" forKey:@"name"];
    NSLog(@"name = %@", [cat valueForKey:name]);

    /// 方法调用
    [cat performSelector:@selector(hunting)];

  // 获取成员变量列表
    unsigned int count = 0;
    Ivar* ivars = class_copyIvarList([self class], &count);

    for (int i = 0; i < count; i++) {
        Ivar var = ivars[i];
        const char* name = ivar_getName(var);
        NSString* key = [NSString stringWithUTF8String:name];
        id value = [self valueForKey:key];
        [aCoder encodeObject:value forKey:key];
    }

    free(ivars);

以上就是这篇文章的全部内容了,希望本文的内容对大家具有一定的参考学习价值,同时欢迎大家进入小编交流群:624212887,一起交流学习,谢谢大家的支持

猜你喜欢

转载自blog.csdn.net/qq_42792413/article/details/83618349