JavaScript模塊化編程那些事

概述

模塊化

是將系統分離成獨立功能的方法,這樣我們可以按需加載功能。

往往當一個項目開發得越來越複雜時,可能會遇到這些些問題,例如:命名衝突、文件依賴等。

總結:在生產的角度,模塊化開發是一種生產方式,這種方式生產效率高,維護成本低。

模塊化開發演變

全局函數

在早期的開發過程中會將重複的代碼封裝搭到函數中,再將一系列的函數放到一個文件中。這種方式存在一些問題:存在汙染全局變量、看不出相互的直接關係。這種方式並不能解決根本的問題:命名衝突和文件依賴。

對象命名空間

通過對象命名空間的形式,從某種程度上解決了變量命名衝突的問題,但是並不能從根本上解決命名衝突。存在問題:內部狀態可被外部改寫、命名空間越來越長。

私有公有成員分離

利用此種方式將函數包裝成一個獨立的作用域,私有空間的變量和函數不會影響到全局作用域。這種方式相當於現在寫插件的形式,解決了變量命名衝突的問題,但是沒有解決降低開發複雜度的問題。

CommonJS

CommonJS規範加載模塊是同步的,也就是說,加載完成才執行後面的操作。

CommonJS規範分為三部分:module(模塊標識)、require(模塊引用)、exports(模塊定義)。 module變量在每個模塊內部,就代表當前模塊; exports屬性是對外的接口,用於導出當前模塊的方法或變量;require()用來加載外部模塊,讀取並執行js文件,返回該模塊的exports對象。

AMD(reuire.js)

AMD也就是異步模塊定義,它採用異步方式加載模塊,主要針對的是瀏覽器端的模塊規範。它通過define方法去定義模塊,require方法去加載模塊。

AMD定義:如果這個模塊還需要依賴其他模塊,那麼define函數的第一個參數,必須是一個數組,指明該模塊的依賴。

<code>require(['modules'], callback);/<code>

第一個參數['modules'],是一個數組,裡面的成員就是需要加載的模塊;第二個參數callback,則是加載成功之後的回調函數。

CMD(sea.js)

CMD即通用模塊定義,CMD規範是國內發展出來的;正如AMD有require.js,CMD有個瀏覽器的實現sea.js。sea.js要解決的問題和require.js一樣,只不過在模塊定義方式和模塊加載方式上有所不同。

<code>define(function (require, exports, module) {
// 模塊代碼
})/<code>

require是可以把其他模塊導入進來的一個參數;exports可以把模塊內的一些屬性和方法導出;module是一個對象,上面存儲了與當前模塊相關聯的一些屬性和方法。CMD是按需加載,推崇依賴就近,延遲執行。文件是提前加載好的,只有在require的時候才去執行文件;

ES6 Module

ES6模塊化汲取CommonJS和AMD的優點,語法簡潔,支持異步加載,未來可以成為瀏覽器和服務器通用的模塊化解決方案。

ES6中模塊的定義:ES6新增了兩個關鍵字:export和import。export用於把模塊裡的內容暴露出來,import用於引入模塊提供的功能。

ES6中模塊的加載,import加載模塊:

<code>import{bar,foo,test,obj} from './lib'
foo();/<code>

注意:可以使用export default命令,為模塊指定默認輸出,一個模塊只能有一個默認輸出,所以export default只能使用一次。

ES6模塊運行機制:ES6模塊是動態引用,如果使用import從一個模塊加載變量(即import foo from 'foo'),變量不會被緩存,而是成為一個指向被加載模塊的引用。等腳本執行時,根據只讀引用,到被加載的那個模塊中去取值。


分享到:


相關文章: