1、使用关联对象动态给分类添加属性
使用关联对象,可以为类添加Category中的属性,我们可以为现有类添加一些实用的方法和属性。
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);
2、hook方法,替换系统方法,拦截方法等
- 当我们发现系统方法的原生实现无法满足我们的某些需求时,我们就可以替换掉系统方法的原生实现,为其添加一些我们的定制化需求。比如:
1.防止崩溃;
2.防止按钮点击过快;
3.从全局上为导航栏添加返回按钮;
4.刷新tableView、collectionView时,自动判断是否显示暂无数据提示图等。 - 我们使用别人的三方库,库里有些方法无法满足我们的需求或者有bug,我们也最好使用黑魔法来处理,而不是直接去该三方库的源码,因为你改了源码后一旦更新了三方库,问题就又出来了。
3、字典模型转换
MJExtension是一个字典模型转换工具,是通过runtime实现的,主要步骤如下:
1)首先使用runtime中的class_copyPropertyList方法,获取类的所有属性,
2)然后遍历每个成员,首先使用property_getName获取属性名,然后使用property_getAttributes获取objc_property_attribute_t,为一个字符串的结果,里面包含属性名称、属性编码类型、原子类型/非原子类型等。
/* 成员变量:
* class_copyIvarList(__unsafe_unretained Class cls, unsigned int *outCount)
* 方法:
* class_copyMethodList(__unsafe_unretained Class cls, unsigned int *outCount)
* 属性:
* class_copyPropertyList(__unsafe_unretained Class cls, unsigned int *outCount)
* 协议:
* class_copyProtocolList(__unsafe_unretained Class cls, unsigned int *outCount)
*/
4、对象自动归档解档
Ivar *ivars = class_copyIvarList([Person class], &count);
5、获取所有的私有属性和方法
Ivar *ivars= class_copyIvarList([UIPageControl class], &count);
Method *memberFuncs = class_copyMethodList([UIPageControl class], &count);
6、消息转发,崩溃拦截
unrecognized selector类型的crash在app众多的crash类型中占着比较大的成分,通常是因为一个对象调用了一个不属于它方法的方法导致的。
我们知道,在一个函数找不到时,runtime提供了三种方式去补救:
1、调用resolveInstanceMethod给个机会让类添加这个实现这个函数
2、调用forwardingTargetForSelector让别的对象去执行这个函数
3、调用forwardInvocation(函数执行器)灵活的将目标函数以其他形式执行。
所以我们可以在这三个方法中添加实现,来响应这个方法,避免崩溃。
7、实现协议转发,进行AB测试
通过runtime的消息转发机制,方法调用,转移到不同的对象中,实现AB方法,避免AB方案代码柔和到同一文件中,通过if和else判断实现。
网友评论