版權聲明:本文爲博主原創文章,轉載請註明出處html
CommonJS, AMD, CMD都是JS模塊化的規範。node
CommonJS是服務器端js模塊化的規範,NodeJS是這種規範的實現。編程
AMD(異步模塊定義)和CMD(通用模塊定義)都是瀏覽器端js模塊化的規範。RequireJS 遵循的是 AMD,SeaJS 遵循的是 CMD。瀏覽器
1、CommonJS服務器
根據CommonJS規範,一個單獨的文件就是一個模塊。加載模塊使用require方法,該方法讀取一個文件並執行,最後返回文件內部的exports對象。因此,定義一個模塊就是寫一個新的js文件,可是最後要將文件的內容exports出來。接下來咱們看一下如何定義模塊和加載模塊。異步
//定義一個module.js文件
var A = function() { console.log('我是定義的模塊'); } //導出這個模塊 //1.第一種返回方式 module.exports = A; //2.第二種返回方式 module.exports.test = A //3.第三種返回方式 exports.test = A;
exports.test = A; //再寫一個test.js文件,去調用剛纔定義好的模塊,這兩個文件在同一個目錄下
var module = require("./module"); //加載這個模塊
//調用這個模塊,不一樣的返回方式用不一樣的方式調用 //1.第一種調用方式 module(); //2.第二種調用方式 module.test(); //3.第三種調用方式 module.test();
module.test(); //接下來咱們去執行這個文件,前提是你本地要安裝node.js,很少說了,本身百度安裝。 //首先打開cmd, cd到這兩個文件所在的目錄下,執行: node test.js
node test.js //輸出結果:我是定義的模塊
當咱們執行 node test.js 的時候,根據 var module = require("./module"); 會加載同一目錄下的module.js文件,並將這個文件的exports對象返回,賦值給module,因此咱們調用 module.test(); 就至關於執行了module.js文件。模塊化
以上就是CommonJS規範下的模塊定義與加載的形式。ui
CommonJS 加載模塊是同步的,因此只有加載完成才能執行後面的操做。像Node.js主要用於服務器的編程,加載的模塊文件通常都已經存在本地硬盤,因此加載起來比較快,不用考慮異步加載的方式,因此CommonJS規範比較適用。但若是是瀏覽器環境,要從服務器加載模塊,這是就必須採用異步模式。因此就有了 AMD CMD 解決方案。 spa
2、AMD(異步模塊定義)code
AMD規範經過define方法去定義模塊,經過require方法去加載模塊。RequireJS實現了這種規範。
AMD只有一個接口:define(id?,dependencies?,factory); 它要在聲明模塊的時候制定全部的依賴(dep),而且還要當作形參傳到factory中。要是沒什麼依賴,就定義簡單的模塊(或者叫獨立的模塊),下面咱們看代碼實現:
//編寫一個module1.js文件 //定義獨立的模塊
define({ methodA: function() { console.log('我是module1的methodA'); }, methodB: function() { console.log('我是module1的methodB'); } }); //編寫一個module2.js文件 //另外一種定義獨立模塊的方式
define(function () { return { methodA: function() { console.log('我是module2的methodA'); }, methodB: function() { console.log('我是module2的methodB'); } }; }); //編寫一個module3.js文件 //定義非獨立的模塊(這個模塊依賴其餘模塊)
define(['module1', 'module2'], function(m1, m2) { return { methodC: function() { m1.methodA(); m2.methodB(); } }; }); //再定義一個main.js,去加載這些個模塊
require(['module3'], function(m3){ m3.methodC(); }); //咱們在一個html文件中去經過RequireJS加載這個main.js //等號右邊的main指的main.js
<script data-main="main" src="require.js"></script>
//瀏覽器控制檯輸出結果
我是module1的methodA 我是module2的methodB
以上就是AMD規範的模塊定義和加載的形式,ReauireJS實現了這種規範。因此咱們的例子也藉助RequireJS去實現。
3、CMD(通用模塊定義)
CMD是SeaJS 在推廣過程當中對模塊定義的規範化產出。
AMD和CMD的區別:
1. 對於依賴的模塊,AMD 是提早執行,CMD 是延遲執行。不過 RequireJS 從 2.0 開始,也改爲能夠延遲執行(根據寫法不一樣,處理方式不一樣)。CMD 推崇 as lazy as possible(儘量的懶加載,也稱爲延遲加載,即在須要的時候才加載)。
2. CMD 推崇依賴就近,AMD 推崇依賴前置。
雖然 AMD 也支持 CMD 的寫法,同時還支持將 require 做爲依賴項傳遞,但 RequireJS 的做者默認是最喜歡上面的寫法,也是官方文檔裏默認的模塊定義寫法。看代碼:
// CMD
define(function(require, exports, module) { var a = require('./a'); a.doSomething(); // 此處略去 100 行
var b = require('./b'); // 依賴能夠就近書寫
b.doSomething(); // ...
}) // AMD 默認推薦的是
define(['./a', './b'], function(a, b) { // 依賴必須一開始就寫好
a.doSomething(); // 此處略去 100 行
b.doSomething(); //...
})
3. AMD 的 API 默認是一個當多個用,CMD 的 API 嚴格區分,推崇職責單一。好比 AMD 裏,require 分全局 require 和局部 require,都叫 require。CMD 裏,沒有全局 require,而是根據模塊系統的完備性,提供 seajs.use 來實現模塊系統的加載啓動。CMD 裏,每一個 API 都簡單純粹。