在oc的runtime机制内有一类方法是可以用来实现类间的方法替换。解决了我们实际开发中诸多常规手段所无法解决的问题。关于Method Swizzling,这里有一篇介绍基本用法的文章

场景

最近出于某种原因,我翻阅了MJRefresh的源码,其中该库就使用了方法交换策略。
在其UICollectionViewUITableView的类别里我发现该库使用了以下代码。于是分析了下其为何如此做的原因。
使用源码如下:


分析

这里先介绍下load的方法的执行方式。load方法是NSObject的方法,NSObject则是oc里大部分类的基类。只要类被添加到runtime中,load的方法均会被调用,而且只会自动被调用一次(除非你自行有调用了次方法,不过一般不会这样做)。其调用方式是执行顺序是 类 -> 子类 ->分类 ,例如A继承与B会先执行B的load再执行A的load,如果分类实现了load方法也是一样会先执行类的load再执行此类的分类里的load方法。因此,此方法是不会被覆盖。

MJRefresh为了替换oc类tableview大专栏  Swizzling的使用e>和collectionview的reloadData以达到调用其自定义的mj_reloadDataBlock,因此实现了分别定义了类别UITableView(MJRefresh)UICollectionView(MJRefresh)并重写了类方法load。在load方法里MJRefresh做了一件事情就是使用runtime里的method_exchangeImplementations方法来实现用mj_reloadData替换tableviewcollectionview里的reloadData方法。
mj_reloadData的方法里我们看到其为了该方法能既能执行原有的reloadData方法又能执行mj_reloadDataBlock,他先调用了[self mj_reloadData]然后有调用了mj_reloadDataBlock。由于方法被交换过,因此此处的[self mj_reloadData]会调用reloadData方法并不会造成死循环,同时也达到了其目的调用原有的reloadData方法。

但是这里我也发现了一个问题,既然方法交换了,如果你调用了[self mj_reloadData]方法则会变成调用reloadData方法,那样岂不是会达到效果?在这里MJRefresh为了不让你这样做,则是将mj_reloadData做为私有方法,没有公开API,你是无法直接调用到的(当然你想调用还是调用的到的,这里就不多做讨论)。

总结

从此处设计,能看出来method_exchangeImplementations的runtime方法的使用场景以及如何运用的思路。在此做了分析记录,也为以后如果碰到一些类似场景提供一些新的解决思路和方式。

Swizzling的使用的更多相关文章

  1. runtime 第四部分method swizzling

    接上一篇 http://www.cnblogs.com/ddavidXu/p/5924597.html 转载来源http://www.jianshu.com/p/6b905584f536 http:/ ...

  2. Objective-C Runtime 运行时之四:Method Swizzling

    理解Method Swizzling是学习runtime机制的一个很好的机会.在此不多做整理,仅翻译由Mattt Thompson发表于nshipster的Method Swizzling一文. Me ...

  3. 【原】iOS动态性(三) Method Swizzling以及AOP编程:在运行时进行代码注入

    概述 今天我们主要讨论iOS runtime中的一种黑色技术,称为Method Swizzling.字面上理解Method Swizzling可能比较晦涩难懂,毕竟不是中文,不过你可以理解为“移花接木 ...

  4. Method Swizzling

    学习博客: http://www.cocoachina.com/ios/20160121/15076.html (这个作者太牛了,写了我一直想知道的类簇的swizz方法) 一. 一般的swizz 先给 ...

  5. Texture tiling and swizzling

    Texture tiling and swizzling 原帖地址:http://fgiesen.wordpress.com If you’re working with images in your ...

  6. oc swizzling 真的好用

    Objective-C的hook方案(一):  Method Swizzling 在没有一个类的实现源码的情况下,想改变其中一个方法的实现,除了继承它重写.和借助类别重名方法暴力抢先之外,还有更加灵活 ...

  7. Objective-C 利用OC的消息机制,使用Method Swizzling进行方法修改

    功能:修改父类不可修改函数方法,函数方法交换 应用场景:假如我们使用的他人提供一个的framework,.m已被打包成二进制.a无法修改源码,只留下.h头文件,那假如代码中某个函数出现了问题可以通过这 ...

  8. Method Swizzling (方法调配)

    Method Swizzling是改变一个selector的实际实现的技术.通过这一技术,我们可以在运行时通过修改类的分发表中selector对应的函数,来修改方法的实现. 例如,我们想跟踪在程序中每 ...

  9. iOS中AOP与Method Swizzling 项目中的应用

    引子:项目中需要对按钮点击事件进行统计分析,现在项目中就是在按钮的响应代码中添加点击事件,非常繁琐.所以使用了AOP(面向切面编程),将统计的业务逻辑统一抽离出来. 项目中添加的开源库:https:/ ...

  10. Method Swizzling和AOP(面向切面编程)实践

    Method Swizzling和AOP(面向切面编程)实践 参考: http://www.cocoachina.com/ios/20150120/10959.html 上一篇介绍了 Objectiv ...

随机推荐

  1. 线段树、最短路径、最小生成树、并查集、二分图匹配、最近公共祖先--C++模板

    线段树(区间修改,区间和): #include <cstdio> #include <iostream> #include <cstring> using name ...

  2. Python 语言基础

    Python 语言基础 Python 开发环境 计算机组成 编程语言(计算机语言)是人们为了控制计算机,而设计的一种符号和文字的组合,从而实现向计算机发出指令. 形式是符号和文字的组合 目的是为了控制 ...

  3. 搜刮一些开源项目的APP

    iOS完整App资源收集 <iOS完整app资源收集>  <GitHub 上有哪些完整的 iOS-App 源码值得参考?> <GitHub 上有哪些完整的 iOS-App ...

  4. scala编程(七)——内建控制结构

    几乎所有的 Scala 的控制结构都会产生某个值.这是函数式语言所采用的方式,程序被看成是计算值的活动,因此程序的控件也应当这么做.另外,指令式语言经常具有三元操作符(如 C,C++和 Java 的? ...

  5. plsql中文显示问号

    1. select userenv('language') from dual 2. 复制查询的值配置系统环境变量 NLS_LANG=AMERICAN_AMERICA.ZHS16GBK 3.配置系统环 ...

  6. java通过jdbc插入中文到mysql显示乱码(问号或者乱码)

    对于很多初学者来说,中文字符编码不相同的问题,是一个很烦躁的问题!! 因为很多时候,我们并不知道,到底是哪一层出现了问题? 在这里稍微做个总结~也怕自己今后忘了!! 其实也就三层: 1.前端页面 2. ...

  7. php函数 之 iconv 不是php的默认函数,也是默认安装的模块。需要安装才能用的。

    windows下最近在做一个小偷程序,需要用到iconv函数把抓取来过的utf-8编码的页面转成gb2312, 发现只有用iconv函数把抓取过来的数据一转码数据就会无缘无故的少一些.  让我郁闷了好 ...

  8. Leetcode9_回文数

    哈哈哈哈哈哈哈太开心了,今天的代码耗时和内存消耗比官方少了一半哈哈 (因为官方用C#写的,我用C++,手动狗头) 题目 判断一个整数是否是回文数.回文数是指正序(从左向右)和倒序(从右向左)读都是一样 ...

  9. AndroidP推出多项AI功能,会不会引发新的隐私担忧?

    让谷歌很"伤心"的是,相比苹果iOS系统的统一,Android系统的碎片化态势实在太严重了.就像已经发布一年多的Android O,其占有率仅有4.6%.主要是因为很多手机厂商都会 ...

  10. Centos7下常见命令

    1:  hostnamectl set-hostname  oldgirl   设置主机名直接生效 2:  hostname oldboy   (暂时生效,重启后恢复原来主机名)