import和require用法示例

Import和require的區別不用多說了,分屬於不同的規範,我們今天分別來試試怎麼使用它們

Common.js

該規範通過exportsmodule.exports進行導出,通過require進行導入,我們看下面兩個簡單的例子:

// b.js
module.exports = {
    bb: 'hello bbb'
}
// c.js
exports.cc = 'hello ccc'
// index.js
var bb = require('./b.js')
var cc = require('./c.js')

console.log(bb) // { bb: 'hello bbb' }
console.log(cc) // { cc: 'hello ccc' }

既然exportsmodule.exports都可以導出,那麼它倆什麼區別呢,其實node爲每個模塊提供一個exports變量,指向module.exports,即:exports.namemodule.exports.name一樣的,但是他倆其實也有細微差別,我們後面會講到。exportsmodule.exports的差別我先總結一下,後面再通過例子驗證:

  1. exports可以重複使用,導出多個對象
  2. module.exports重複使用時,以最後一個module.exports爲準
  3. exportsmodule.exports一起使用時,exports的對象都無法導出

我們一個一個來驗證:

/* exports可以重複使用,導出多個對象 */

// c.js
exports.aa = 'hello aa'
exports.bb = 'hello bb'
exports.cc = 'hello cc'

// index.js
var cc = require('./c.js')
console.log(cc) // { aa: 'hello aa', bb: 'hello bb', cc: 'hello cc' }
/* module.exports重複使用時,以最後一個module.exports爲準 */

// c.js
module.exports = {
    aa: 'hello aaa'
}
module.exports = {
    bb: 'hello bbb'
}

// index.js
var cc = require('./c.js')
console.log(cc) // { bb: 'hello bbb' }
/* exports和module.exports一起使用時,exports的對象都無法導出 */

// c.js
exports.aa = 'hello aaa'
module.exports = {
    bb: 'hello bbb'
}
exports.cc = 'hello ccc'

// index.js
var cc = require('./c.js')
console.log(cc) // { bb: 'hello bbb' }

我剛剛說過exports.namemodule.exports.name一樣的,但是他倆其實也有細微差別,我們先說說他倆一樣的地方:

// c.js
exports.aa = 'hello aaa'
module.exports.bb = 'hello bbb'
exports.cc = 'hello ccc'
module.exports.dd = 'hello ddd'

// index.js
var cc = require('./c.js')
console.log(cc) // { aa: 'hello aaa', bb: 'hello bbb', cc: 'hello ccc', dd: 'hello ddd' }

爲了看它倆的差別,我們在中間插入一個module.exports看看:

// c.js
exports.aa = 'hello aaa'
module.exports.bb = 'hello bbb'
module.exports = {
    main: 'hello main'
}
exports.cc = 'hello ccc'
module.exports.dd = 'hello ddd'

// index.js
var cc = require('./c.js')
console.log(cc) // { main: 'hello main', dd: 'hello ddd' }

可見,三種寫法都使用的時候,只有module.exports和處於module.exports下方的module.exports.dd指向的對象可以導出

ES6

es6使用export導出,使用import導入,我們先舉幾個簡單的例子:

// a.js
export var aa = 110
export const bb = 'hello bb'

var cc = 2
export {
    cc
}

// index.js
import * as all from './a.mjs'
console.log(all) // [Module] { aa: 110, bb: 'hello bb', cc: 2 }

注意,export的實質是暴露接口,在接口名與模塊內部變量之間,建立一個一一對應的關係,所以以下的寫法是有問題的:

// 以下寫法均會報錯

var kkm = 1
export kkm

export 'hello'

export {
    kk: 'hello'
}

有一種情況也會報錯:

// 不報錯
var cc = 2
export {
    cc
}

// 報錯
var cc = 2
export {
    cc: cc
}

as關鍵字
as關鍵字相當於給導出和導入的接口名起的別名,exportimport均可以使用

// b.js
const bb = 'hello bb'
export {bb as bbInter}

// index.js
import * as all from './b.js'
console.log(all) // { bbInter: 'hello bb' }
// b.js
const bb = 'hello bb'
export {bb as bbInter}

// index.js
import {bbInter as bb} from './b.js'
console.log(bb) // hello bb

default關鍵字
defalut其實是一種簡寫的寫法,相當於將模塊中一個名爲default的變量作爲接口暴露出去,舉例子:

export default 54;

// 等價於
var dind = 54;
export {dind as default};

因此,default只能export一次,如果多次export,則會報錯Duplicate export of 'default'

export default對應的import寫法:

import bb from './b.js'

// 等價於
import {default as bb} from './b.js'

和commonJs規範不同,export暴露的是接口,可以認爲是指針,即export的變量發生變化時,import的變量也會發生變化,我們來測試一下:

// b.js

var dind = 54;
// 變化
setTimeout(() => {
    dind = 'change'
}, 2000)

export {dind as default};
//index.js

import bb from './b.js'

setInterval(() => {
    console.log(bb)
}, 500);

index.js運行結果:

54
54
54
change
change
change
...
發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章