對於大多數node初學者而言, module.exports應該都是理解的, 但多出來一個exports獲取就有些疑問了javascript
疑問一: 既然有module.exports了爲何還要有exports?java
疑問二: 二者有什麼區別?node
首先, 官網是這麼回答的express
The exports
variable is available within a module's file-level scope, and is assigned the value of module.exports
before the module is evaluated. app
It allows a shortcut, so that module.exports.f = ...
can be written more succinctly as exports.f = ...
. 函數
也就是說, exports至關於一個快捷方式,exports.f = ...
. 確定是比 module.exports.f = ... 寫起來方便一些。下面附上一段express源碼中的使用你就明白了。ui
exports = module.exports = createApplication; exports.mime = connect.mime; exports.application = proto; exports.request = req; exports.response = res; function createApplication() { var app = connect(); merge(app, proto); app.request = { __proto__: req, app: app }; app.response = { __proto__: res, app: app }; app.init(); return app; }
其實exports是將指針執行module.exports對象, 若是你像exports = function(){}這樣至關於改變了exports原來的指向, 也就沒法被導出, 爲何?先看官網給的相似實現:lua
function require(/* ... */) { const module = { exports: {} }; ((module, exports) => { // 你的模塊代碼在這。在這個例子中,定義了一個函數。 function someFunc() {} exports = someFunc; // 此時,exports 再也不是一個 module.exports 的快捷方式, // 且這個模塊依然導出一個空的默認對象。 module.exports = someFunc; // 此時,該模塊導出 someFunc,而不是默認對象。 })(module, module.exports); return module.exports; }
根據上面的代碼能夠看出exports是模塊內部一個形參對象, 若是給exports對象添加屬性是能夠導出的, 由於指針並未改變, 但若是賦值一個對象就不行了, 由於指針已經改變了,最後導出的是module.exportsspa