###### tags: `第14屆IT邦鐵人賽文章`
# 【在 iOS 開發路上的大小事2-Day10】MVC vs MVVM!MVVM 是什麼?能吃嗎?(上)
## 免責聲明?
這篇是以我自己理解的內容來記錄
所以哪邊有理解錯誤的地方,再麻煩跟我說,感謝~
## 前情提要
在開發上,有著許多的 Design Pattern (設計模式)
像是 MVC (Model-View-Controller)、MVVM (Model-View-ViewModel)、MVP (Model-View-Presenter) 等
以 iOS App 來說,Apple 自己是比較傾向 MVC 架構

▲ 圖取自 [Apple Developer Documentation](https://developer.apple.com/library/archive/documentation/General/Conceptual/DevPedia-CocoaCore/MVC.html)
但實際上開發,卻很常會變成 Model+ViewController 的架構
你說,原本的 View 去哪裡了,他去跟 Controller 合為一體了~
然後 App 規模在大一點,可能會變成 Massive View Controller
因為 UI (也就是 View) 跟邏輯運算 (也就是 Controller) 都混在一起
這樣在維護、測試上就會不太方便,所以就延伸出許多的設計模式來改善 MVC 架構
像是開頭提到的 MVVM (Model-View-ViewModel)、MVP (Model-View-Presenter)
## 本篇主角1-MVC
再用一次上面的圖 (哈哈哈哈)

▲ 圖取自 [Apple Developer Documentation](https://developer.apple.com/library/archive/documentation/General/Conceptual/DevPedia-CocoaCore/MVC.html)
### MVC 的各司其職
先來介紹 MVC 各層所負責的事情
* Model:
* 資料儲存、資料型別定義,當資料有變化時,通知 Controller
* View:
* 顯示 UI 元件、並在使用者觸發動作時通知 Controller
* Controller:
* 負責在使用者有動作的時候去執行特定工作、要求 Model 更新狀態、在 Model 有變化時更新 View 的內容來顯示這些變化
### MVC 的優點
> 1. 提高程式的可維護性,MVC 將一個功能區分成許多片段,讓程式變得容易維護
> 2. 在 MVC 中,同一個 Model 可以被不同的 View 重用,提高了程式碼的可重用性
> 3. MVC 的架構容易識別,可以讓工程師快速掌握項目的結構
> 4. MVC 將一個功能分成了三部分,因此多個工程師可以同時開發不同部分的程式碼
### MVC 的缺點
> 1. View 與 Controller 綁住了,不易進行 Unit Test
> 2. 要花費較多的時間進行前置規劃
> 3. 要管理較多檔案
## 本篇主角2- MVVM

▲ 圖取自網路
### MVVM 的各司其職
先來介紹 MVVM 各層所負責的事情
* Model:
* 與原先 MVC 中的 M (Model) 是一樣的,用來資料儲存、資料型別定義
* **只能與** ViewModel 進行溝通,**不能與** View/ViewController 直接溝通
* ViewModel:
* 負責將 Model 的資料轉換成 View/ViewController 所需的格式
* 處理網路請求的部分
* View/ViewController:
* 接收 ViewModel 的資料來做 UI 畫面呈現、與使用者互動
* **只能與** ViewModel 進行溝通以及 Data Binding
* **只能透過** ViewModel 來跟 Model 進行間接溝通
簡單來說,
Model **只能與** ViewModel 做互動,**不能與** View/ViewController 互動
ViewModel **會與** Model **還有** View/ViewController 做互動
View/ViewController **只能與** ViewModel 做互動,**不能與** Model 互動
### MVVM 的優點
> 1. 用 Data Binding 的方式與 View/ViewController 溝通,使 ViewModel 可以不用知道是哪個 View/ViewController
> 2. 商業邏輯不用與 UI 綁在一起,讓 ViewController 可以瘦身
> 3. ViewModel 相對容易執行單元測試 (Unit Test)
### MVVM 的缺點
> 1. 大型的應用程式中,Data Binding 會導致相當大的記憶體消耗
> 2. 無法簡單重用 View/ViewController,因為與 ViewModel 綁定的關係
> 3. 並無強硬規定 View/ViewController 跟 ViewModel 的關係
> (Ex:單向 or 雙向溝通)
> 4. 不易除錯,不容易找出 bug 是在 Model 還是 View
## 參考資料
1. https://front-chef.coderbridge.io/2021/02/27/mvc-mvvm/
2. https://developer.apple.com/library/archive/documentation/General/Conceptual/DevPedia-CocoaCore/MVC.html
3. https://chiahsien.github.io/post/common-ios-architecture-from-mvc-to-viper-with-redux/
4. https://www.tpisoftware.com/tpu/articleDetails/1952
5. https://medium.com/swift-thing/%E7%A8%8B%E5%BC%8F%E5%AD%B8%E7%BF%92%E7%AD%86%E8%A8%98-model-view-controller-5a6690e76563
6. https://ithelp.ithome.com.tw/articles/10254585