Runtime

1、runtime 为何物

引题:为什么其他语言里叫函数调用, Objective-C里则是给对象发消息呢?
这里其中就是因为runtime模块的存在,那么runtime到底是何物呢?
runtime就是一个由C和汇编语言编写的一个库,注意了,它仅仅是一个库,而不是OC这门语言的特性,而且这个库苹果是开源的,大家有兴趣深究的话可以去下载这个库来深究,这是代码的下载链接:http://www.opensource.apple.com/tarballs/objc4/

2、runtime 术语基础

代码重写命令:clang -rewrite-objc 源代码文件名

1、SEL:
2、id:
3、Class:

struct objc_class {
    Class isa  OBJC_ISA_AVAILABILITY;   // 指向metaclass
#if !__OBJC2__
    Class super_class                                        OBJC2_UNAVAILABLE;// 指向其父类        
    const char *name                                         OBJC2_UNAVAILABLE;// 名称
    long version                                             OBJC2_UNAVAILABLE;//  版本信息,可进行修改,默认为0
    long info                                                OBJC2_UNAVAILABLE;//  标识,表示类或对象
    long instance_size                                       OBJC2_UNAVAILABLE;//  对象大小
    struct objc_ivar_list *ivars                             OBJC2_UNAVAILABLE;//  成员变量列表
    struct objc_method_list **methodLists                    OBJC2_UNAVAILABLE;//  方法列表,与info相关,分类方法或对象方法
    struct objc_cache *cache                                 OBJC2_UNAVAILABLE;//  方法缓存
    struct objc_protocol_list *protocols                     OBJC2_UNAVAILABLE;//  协议列表
#endif

} OBJC2_UNAVAILABLE;
/* Use Class instead of struct objc_class * */

4、Method:
5、Ivar:
6、IMP:
7、Cache:
8、Property:

3、runtime之动态方法解析

resolveInstanceMethod:resolveClassMethod:动态添加方法实现
Objective-C Runtime Programming Guide

4、runtime之消息转发(Messaging)

1、重定向:通过重载 - (id)forwardingTargetForSelector:(SEL)aSelector方法替换消息的接受者为其他对象
2、转发:当动态方法解析不作处理返回NO时,消息转发机制会被触发。在这时-forwardInvocation:方法会被执行,我们可以重写这个方法来定义我们的转发逻辑
注意:-forwardInvocation:方法只有在消息接收对象中无法正常响应消息时才会被调用
3、转发和多继承

5、runtime之关联(Associated Objects)

 enum {
     OBJC_ASSOCIATION_ASSIGN  = 0,
     OBJC_ASSOCIATION_RETAIN_NONATOMIC  = 1,
     OBJC_ASSOCIATION_COPY_NONATOMIC  = 3,
     OBJC_ASSOCIATION_RETAIN  = 01401,
 };

设置属性赋值:void objc_setAssociatedObject ( id object, const void *key, id value, objc_AssociationPolicy policy );
获取属性值:id objc_getAssociatedObject ( id object, const void *key );
移除属性:void objc_removeAssociatedObjects ( id object );

6、runtime & Method Swizzling

系统类的方法实现部分替换:Method class_getInstanceMethod(Class cls, SEL name) void method_exchangeImplementations(Method m1, Method m2)
覆盖系统方法:IMP class_replaceMethod(Class cls, SEL name, IMP imp, const char *types)

7、runtime之其它实践

1、对象拷贝:id object_copy(id obj, size_t size)
2、对象释放 id object_dispose(id obj)
3、更改对象的类/获取对象的类 Class object_setClass(id obj, Class cls) / Class object_getClass(id obj)
4、获取对象的类名 constchar *object_getClassName(id obj)
5、给一个类添加方法 BOOL class_addMethod(Class cls,SEL name,IMP imp, const char *types)
6、获取一个类的所有方法:Method *class_copyMethodList(Class cls, unsigned int *outCount)
获取方法名:SEL method_getName(Method m)
7、获取一个类的所有属性:objc_property_t *class_copyPropertyList(Class cls, unsigned int *outCount)
获取属性的名称:const char *property_getName(objc_property_t property)
8、获取/设置类的属性变量:Ivar object_getInstanceVariable(id obj, const char *name, void **outValue)
9、判断类的某个属性的类型:Ivar class_getInstanceVariable(Class cls, const char *name)
const char *ivar_getTypeEncoding(Ivar v)

作业:
1、创建不同类型的属性
2、替换系统方法
2、用纯C语言编写一个TableView列表

摘自:http://yulingtianxia.com/blog/2014/11/05/objective-c-runtime/