MVC與MVVM架構模式詳解:原理、區別與JavaScript實現

Hi,我是布蘭妮甜 !在當今復雜的前端開發領域,如何組織代碼結構一直是開發者面臨的核心挑戰。MVCMVVM作為兩種經典的架構模式,為前端應用提供了清晰的責任劃分和可維護的代碼組織方案。本文將深入探討這兩種模式的原理、實現差異以及在實際項目中的應用場景,通過JavaScript代碼示例展示它們的核心思想,幫助開發者理解如何根據項目需求選擇合適的架構模式。


文章目錄

    • 一、架構模式概述
    • 二、MVC架構模式
      • 2.1 MVC基本概念
      • 2.2 MVC數據流
      • 2.3 JavaScript實現示例
      • 2.4 MVC的優缺點
    • 三、MVVM架構模式
      • 3.1 MVVM基本概念
      • 3.2 MVVM數據流
      • 3.3 JavaScript實現示例(使用Vue.js)
      • 3.4 MVVM的優缺點
    • 四、MVC與MVVM的比較
    • 五、現代框架中的實現
      • 5.1 Vue.js - 典型的MVVM實現
      • 5.2 React - 類MVVM模式
      • 5.3 Angular - 完整的MVVM實現
    • 六、如何選擇架構模式
    • 七、總結


一、架構模式概述

在軟件開發中,架構模式決定了代碼的組織方式,影響著應用程序的可維護性、可擴展性和可測試性。MVC(Model-View-Controller)和MVVM(Model-View-ViewModel)是兩種廣泛使用的架構模式,特別在前端開發中尤為重要。

二、MVC架構模式

2.1 MVC基本概念

  • Model(模型): 負責數據和業務邏輯
  • View(視圖): 負責用戶界面展示
  • Controller(控制器): 接收用戶輸入,協調Model和View

2.2 MVC數據流

  1. 用戶與View交互(如點擊按鈕)
  2. View將用戶操作傳遞給Controller
  3. Controller處理用戶輸入,可能需要更新Model
  4. Model將變更通知View
  5. View從Model獲取最新數據并更新界面

2.3 JavaScript實現示例

// Model
class UserModel {constructor() {this.users = [];this.listeners = [];}addUser(user) {this.users.push(user);this.notifyListeners();}addListener(listener) {this.listeners.push(listener);}notifyListeners() {this.listeners.forEach(listener => listener(this.users));}
}// View
class UserView {constructor(controller) {this.controller = controller;this.userList = document.getElementById('user-list');this.addButton = document.getElementById('add-user-btn');this.nameInput = document.getElementById('user-name-input');this.addButton.addEventListener('click', () => {const name = this.nameInput.value;if (name) {this.controller.handleAddUser(name);this.nameInput.value = '';}});}update(users) {this.userList.innerHTML = users.map(user => `<li>${user}</li>`).join('');}
}// Controller
class UserController {constructor(model) {this.model = model;}handleAddUser(name) {this.model.addUser(name);}
}// 初始化
const model = new UserModel();
const controller = new UserController(model);
const view = new UserView(controller);model.addListener(users => view.update(users));

2.4 MVC的優缺點

優點:

  • 關注點分離,職責清晰
  • 可維護性強
  • 視圖與模型解耦,可復用視圖

缺點:

  • 對于復雜界面,控制器可能變得臃腫
  • 視圖與模型間仍有直接或間接的依賴
  • 在現代富客戶端應用中可能不夠靈活

三、MVVM架構模式

3.1 MVVM基本概念

  • Model(模型): 負責數據和業務邏輯(與MVC相同)
  • View(視圖): 用戶界面展示(與MVC相同)
  • ViewModel(視圖模型): 暴露數據和命令供View使用,充當View與Model之間的橋梁

3.2 MVVM數據流

  1. View通過數據綁定與ViewModel交互
  2. ViewModel從Model獲取數據并暴露給View
  3. 用戶操作觸發ViewModel中的命令
  4. ViewModel處理命令,可能更新Model
  5. Model變更通過數據綁定自動反映到View

3.3 JavaScript實現示例(使用Vue.js)

// Model (與MVC示例相同)
class UserModel {constructor() {this.users = [];}addUser(user) {this.users.push(user);}getUsers() {return [...this.users];}
}// ViewModel (Vue實例)
const app = new Vue({el: '#app',data: {model: new UserModel(),newUserName: ''},computed: {users() {return this.model.getUsers();}},methods: {addUser() {if (this.newUserName) {this.model.addUser(this.newUserName);this.newUserName = '';}}}
});<!-- View (HTML) -->
<div id="app"><input v-model="newUserName" placeholder="Enter user name"><button @click="addUser">Add User</button><ul><li v-for="user in users" :key="user">{{ user }}</li></ul>
</div>

3.4 MVVM的優缺點

優點:

  • 數據綁定減少樣板代碼
  • 視圖與模型完全解耦
  • 更易于單元測試
  • 適合數據驅動的UI

缺點:

  • 數據綁定可能帶來性能問題(如果實現不當)
  • 調試復雜數據流可能困難
  • 學習曲線較陡

四、MVC與MVVM的比較

特性MVCMVVM
核心思想關注點分離數據驅動視圖
通信方式Controller中介數據綁定
適合場景傳統Web應用現代富客戶端應用
復雜度中等較高
測試便利性需要模擬視圖易于單元測試
典型框架Backbone.js, Spring MVCVue.js, Knockout.js

五、現代框架中的實現

5.1 Vue.js - 典型的MVVM實現

Vue.js 是一個典型的 MVVM 框架,其核心特性完美體現了 MVVM 模式的思想:

// Model
const userModel = {users: [],addUser(user) {this.users.push(user)},getUsers() {return [...this.users]}
}// ViewModel (Vue實例)
new Vue({el: '#app',data: {newUserName: '',users: []},created() {// 初始化數據this.users = userModel.getUsers()},methods: {addUser() {if (this.newUserName) {userModel.addUser(this.newUserName)this.users = userModel.getUsers()this.newUserName = ''}}}
})
<!-- View -->
<div id="app"><input v-model="newUserName" placeholder="輸入用戶名"><button @click="addUser">添加用戶</button><ul><li v-for="user in users">{{ user }}</li></ul>
</div>

Vue.js 的 MVVM 實現特點:

  1. 數據綁定:通過 v-model 實現雙向數據綁定
  2. 響應式系統:自動追蹤依賴并更新視圖
  3. 組件化:將 View 和 ViewModel 封裝在組件中
  4. 指令系統v-forv-if 等指令簡化視圖邏輯

Vue 3 的 Composition API 進一步強化了 MVVM 模式:

import { ref, reactive } from 'vue'export default {setup() {const newUserName = ref('')const state = reactive({users: []})const addUser = () => {if (newUserName.value) {userModel.addUser(newUserName.value)state.users = userModel.getUsers()newUserName.value = ''}}return {newUserName,users: state.users,addUser}}
}

這種實現方式:

  • 更清晰地分離了關注點
  • 提供了更好的類型推斷
  • 使邏輯復用更加容易
  • 保持了 MVVM 的核心思想

5.2 React - 類MVVM模式

雖然React官方不宣稱使用MVVM,但其思想與MVVM相似:

// Model
const userModel = {users: [],addUser(user) {this.users.push(user);},getUsers() {return [...this.users];}
};// ViewModel組件
function UserList() {const [users, setUsers] = useState([]);const [newUser, setNewUser] = useState('');const handleAddUser = () => {if (newUser) {userModel.addUser(newUser);setUsers(userModel.getUsers());setNewUser('');}};return (<div><input value={newUser}onChange={(e) => setNewUser(e.target.value)}placeholder="Enter user name"/><button onClick={handleAddUser}>Add User</button><ul>{users.map((user, index) => (<li key={index}>{user}</li>))}</ul></div>);
}

5.3 Angular - 完整的MVVM實現

Angular明確采用MVVM模式:

// Model
export interface User {id: number;name: string;
}// ViewModel (Component)
@Component({selector: 'app-user-list',template: `<input [(ngModel)]="newUserName" placeholder="Enter user name"><button (click)="addUser()">Add User</button><ul><li *ngFor="let user of users">{{user.name}}</li></ul>`
})
export class UserListComponent {users: User[] = [];newUserName = '';private nextId = 1;addUser() {if (this.newUserName) {this.users.push({id: this.nextId++,name: this.newUserName});this.newUserName = '';}}
}

六、如何選擇架構模式

  1. 項目復雜度:簡單項目可能不需要MVVM的復雜性
  2. 團隊熟悉度:團隊對模式的熟悉程度影響開發效率
  3. 框架選擇:所選框架可能傾向于某種模式
  4. 測試需求:MVVM通常更易于單元測試
  5. 數據綁定需求:數據密集型UI更適合MVVM

七、總結

MVC和MVVM都是優秀的架構模式,各有適用場景。理解它們的原理和區別有助于為項目選擇合適的設計方案。隨著前端技術的發展,現代框架往往融合了多種模式的優點,開發者應根據實際需求靈活應用這些架構思想。

本文來自互聯網用戶投稿,該文觀點僅代表作者本人,不代表本站立場。本站僅提供信息存儲空間服務,不擁有所有權,不承擔相關法律責任。
如若轉載,請注明出處:http://www.pswp.cn/diannao/89979.shtml
繁體地址,請注明出處:http://hk.pswp.cn/diannao/89979.shtml
英文地址,請注明出處:http://en.pswp.cn/diannao/89979.shtml

如若內容造成侵權/違法違規/事實不符,請聯系多彩編程網進行投訴反饋email:809451989@qq.com,一經查實,立即刪除!

相關文章

從小白到進階:解鎖linux與c語言高級編程知識點嵌入式開發的任督二脈(2)

【硬核揭秘】Linux與C高級編程&#xff1a;從入門到精通&#xff0c;你的全棧之路&#xff01; 第三部分&#xff1a;Shell腳本編程——自動化你的Linux世界&#xff0c;讓效率飛起來&#xff01; 嘿&#xff0c;各位C語言的“卷王”們&#xff01; 在Linux的世界里&#xf…

鎖和事務的關系

事務的4大特性(ACID) 原子性&#xff08;Atomicity&#xff09;&#xff1a;事務被視為一個單一的、不可分割的工作單元一致性&#xff08;Consistency&#xff09;&#xff1a;事務執行前后&#xff0c;數據庫從一個一致狀態轉變為另一個一致狀態&#xff0c;并且強制執行所有…

電動車信用免押小程序免押租賃小程序php方案

電動車信用免押租賃小程序&#xff0c;免押租小程序&#xff0c;信用免押接口申請、對接開發&#xff0c;可源碼搭建&#xff0c;可二開或定制。開發語言后端php&#xff0c;前端uniapp。可二開定制 在線選擇門店&#xff0c;選擇車輛類型&#xff0c;選擇租賃方式&#xff08…

機器學習在智能安防中的應用:視頻監控與異常行為檢測

隨著人工智能技術的飛速發展&#xff0c;智能安防領域正經歷著一場深刻的變革。智能安防通過整合先進的信息技術&#xff0c;如物聯網&#xff08;IoT&#xff09;、大數據和機器學習&#xff0c;能夠實現從傳統的被動防御到主動預防的轉變。機器學習技術在智能安防中的應用尤為…

MySQL中DROP、DELETE與TRUNCATE的深度解析

在MySQL數據庫操作中&#xff0c;DROP、DELETE和TRUNCATE是三個常用的數據操作命令&#xff0c;它們都可以用于刪除數據&#xff0c;但在功能、執行效率、事務處理以及對表結構的影響等方面存在顯著差異。本文將從多個維度對這三個命令進行詳細對比和解析&#xff0c;幫助讀者更…

一條 SQL 語句的內部執行流程詳解(MySQL為例)

當執行如下 SQL&#xff1a; SELECT * FROM users WHERE id 1;在數據庫內部&#xff0c;其實會經歷多個復雜且有序的階段。以下是 MySQL&#xff08;InnoDB 引擎&#xff09;中 SQL 查詢語句從發送到結果返回的完整執行流程。 客戶端連接階段 客戶端&#xff08;如 JDBC、My…

超詳細yolo8/11-detect目標檢測全流程概述:配置環境、數據標注、訓練、驗證/預測、onnx部署(c++/python)詳解

文章目錄 一、配置環境二、數據標注三、模型訓練四、驗證預測五、onnx部署c 版python版本 一、配置環境 我的都是在Linux系統下&#xff0c;訓練部署的&#xff1b;模型訓練之前&#xff0c;需要配置好環境&#xff0c;Anaconda、顯卡驅動、cuda、cudnn、pytorch等&#xff1b…

阿里云Flink:開啟大數據實時處理新時代

走進阿里云 Flink 在大數據處理的廣袤領域中&#xff0c;阿里云 Flink 猶如一顆璀璨的明星&#xff0c;占據著舉足輕重的地位。隨著數據量呈指數級增長&#xff0c;企業對數據處理的實時性、高效性和準確性提出了前所未有的挑戰 。傳統的數據處理方式逐漸難以滿足這些嚴苛的需…

【Linux】基礎開發工具(1)

1. 軟件包管理器 1.1 什么是軟件包 在Linux下安裝軟件, ?個常用的辦法是下載到程序的源代碼, 并進行編譯, 得到可執行程序. 但是這樣太麻煩了, 于是有些人把?些常?的軟件提前編譯好, 做成軟件包(可以理解成windows上 的安裝程序)放在?個服務器上, 通過包管理器可以很?便…

藍橋杯51單片機設計

#超聲波原理# ①超聲波測距原理&#xff1a;聲波反射原理 聲波分類&#xff1a; 超聲波測距原理 超聲波頻率越高&#xff0c;波長越短&#xff0c;反身性越強&#xff0c;衍射性越弱 ②超聲波模塊原理 發射原理 跳線帽 接收原理 問題&#xff1a; &#xff11;.超聲波發射模塊需…

【LeetCode 熱題 100】240. 搜索二維矩陣 II——排除法

Problem: 240. 搜索二維矩陣 II 編寫一個高效的算法來搜索 m x n 矩陣 matrix 中的一個目標值 target 。該矩陣具有以下特性&#xff1a; 每行的元素從左到右升序排列。 每列的元素從上到下升序排列。 文章目錄 整體思路完整代碼時空復雜度時間復雜度&#xff1a;O(M N)空間復…

Android Input 系列專題【inputflinger事件的讀取與分發】

Android輸入系統在native中的核心工作就是&#xff0c;從Linux驅動設備節點中讀取事件&#xff0c;然后將這個事件進行分發&#xff0c;這兩項工作分別交給了InputReader和InputDispatcher來做。 他們的源碼都屬于native層inputflinger里面的一部分&#xff0c;如下架構&#…

【大模型LLM】GPU計算效率評估指標與優化方法:吞吐率

GPU計算效率評估指標與優化方法&#xff1a;吞吐率 一、核心效率指標二、大模型吞吐率&#xff08;Large Model Throughput&#xff09;三、關鍵性能瓶頸分析四、實際測量工具五、優化策略總結 一、核心效率指標 吞吐率&#xff08;Throughput&#xff09; 定義&#xff1a;單位…

Nestjs框架: 集成 Prisma

概述 在 NestJS 的官方文檔中&#xff0c;有兩處對數據庫進行了介紹 第一處位于左側“Techniques&#xff08;技術&#xff09;”部分下的“數據庫”板塊&#xff0c;中文文檔里同樣有這個位置。 Database 第二處是下面的“Recipes (秘籍)”板塊&#xff0c;這里有多個部分都與…

CppCon 2018 學習:What Do We Mean When We Say Nothing At All?

提供的內容深入探討了C編程中的一些關鍵概念&#xff0c;特別是如何編寫清晰、易維護的代碼&#xff0c;并展示了一些C17的新特性。我將對這些內容做中文的解釋和總結。 1. 良好的代碼設計原則 什么是“良好的代碼”&#xff1f; 能工作&#xff1a;代碼實現了預期功能。能在…

C語言中的輸入輸出函數:構建程序交互的基石

在C語言的世界里&#xff0c;輸入輸出&#xff08;I/O&#xff09;操作是程序與用戶或外部數據源進行交互的基本方式。無論是從鍵盤接收用戶輸入&#xff0c;還是將處理結果顯示到屏幕上&#xff0c;亦或是讀寫文件&#xff0c;都離不開C語言提供的輸入輸出函數。本文將深入探討…

高速信號眼圖

橫軸體系時域的抖動大小&#xff1b;縱軸體現電壓的噪聲。 噪聲越大&#xff0c;眼高越小。 抖動越大&#xff0c;眼寬越窄。 眼圖的模板是定義好的最大jitter和噪聲的模板范圍。就是信號的不可觸碰區域。信號波形不能夠觸碰到模板或者進行模板中。也就是眼圖中的線軌跡要在眼…

VisualSVN Server 禁止的特殊符號 導致的。具體分析如下:錯誤提示解讀

是由于 文件夾名稱中包含了 VisualSVN Server 禁止的特殊符號 導致的。具體分析如下&#xff1a; 錯誤提示解讀 錯誤信息明確說明&#xff1a; Folder name cannot contain following symbols < > : " / | and start or end by period. 即 文件夾名稱不能包含以下…

再見,WebSecurityConfigurerAdapter!你好,SecurityFilterChain

對于許多經驗豐富的 Spring開發者來說&#xff0c;WebSecurityConfigurerAdapter 是一個再熟悉不過的名字。在很長一段時間里&#xff0c;它幾乎是所有 Spring Security 配置的起點和核心。然而&#xff0c;隨著 Spring Boot 3.x 和 Spring Security 6.x 的普及&#xff0c;這個…

web前端面試-- MVC、MVP、MVVM 架構模式對比

MVC、MVP、MVVM 架構模式對比 基本概念 這三種都是用于分離用戶界面(UI)與業務邏輯的架構模式&#xff0c;旨在提高代碼的可維護性、可測試性和可擴展性。 1. MVC (Model-View-Controller) 核心結構&#xff1a; Model&#xff1a;數據模型和業務邏輯View&#xff1a;用戶界面展…