題目: 假設我們有一個ViewController,
Category A(ViewController),
Category B(ViewController),
Category C(ViewController)
4個文件, 其中3個category中都實現了自定義viewDidLoad方法, 會對ViewController中的ViewDidLoad方法進行方法替換, 那么依次替換后(A B C)的方法執行順序是什么呢?
記method_exchangeImplementations(Method _Nonnullm1, Method _Nonnullm2) 方法多次執行的代碼執行邏輯.
假設我們的方法替換由我們指定的一個category D來完成3次交換過程,代碼如下圖

那么接下來我們就詳細來探究一下每次追加一個方法交換,會對原方法有什么改變。
1. IMP方法實現交換
第一趟: 交換 原方法 和 A

ViewController的原方法如下

在category A中方法如下:

交換后類實例方法和IMP的指向如下:

方法調用:
交換后, 調用class 0(ViewController)的selector0, 會調用category A的IMP1, 既打印 “extension A viewDidLoad”, 然后調用了category A的Sel, 就會去執行 class 0(ViewController)的IMP, 既打印 “origin viewDidLoad method”;
控制台打印如下:

接下來追加方法交換: 在原有方法交換基礎上 追加 交換原方法 和 B

在category B中方法如下:

交換后類實例方法和IMP的指向如下:

代碼執行: 執行Sel0—>IMP2—>SelB—>IMP1—>SelA—>IMP, 所以控制台輸入順序為 B A 0
控制台輸出如下:

繼續追加方法交換: 在原有方法交換基礎上 追加 交換原方法 和 C

在category C中方法如下:

交換后類實例方法和IMP的指向如下:

代碼執行: 先執行Sel0-->IMP3—>SelC—>IMP2—>SelB—>IMP1—>SelA—>IMP, 所以控制台輸入順序為 C B A 0
控制台輸出如下:

由此可以推理出來:
我們依次追加n個對原方法交換, 那么class 0對應的Sel0執行的IMP會偏移指向最后一個方法交換的Sel, 那么就會按照交換前后順序執行邏輯.
Demo地址: https://github.com/Winerywine/MethodExchange.git
