CommonJS与ES6Module的区别

tech2026-10-05  2

不同点

1.使用CommonJS引用的变量可以修改,若是引用类型变量,会影响到被引用模块的值。ES6模块中引用的值为只读模式,不可修改(但可以修改对象类型的属性)。

2.require属于运行时加载,只有当代码在运行的时候才会得到引用的对象,导致完全没办法在编译时做“静态优化”;import属于编译时加载,即 ES6 可以在编译时就完成模块加载。

3.ES6模块中,export语句输出的接口,与其对应的值是动态绑定关系,即通过该接口,可以取到模块内部实时的值。

相同点

require和import都会执行引用的模块

3.当使用require命令加载某个模块时,就会运行整个模块的代码。

4.当使用require命令加载同一个模块时,不会再执行该模块,而是取到缓存之中的值。也就是说,CommonJS模块无论加载多少次,都只会在第一次加载时运行一次,以后再加载,就返回第一次运行的结果,除非手动清除系统缓存。

5.循环加载时,属于加载时执行。即脚本代码在require的时候,就会全部执行。一旦出现某个模块被"循环加载",就只输出已经执行的部分,还未执行的部分不会输出。

3, 4, 5可以使用同一个例子说明 // b.js exports.done = false let a = require('./a.js') console.log('b.js-1', a.done) exports.done = true console.log('b.js-2', '执行完毕') // a.js exports.done = false let b = require('./b.js') console.log('a.js-1', b.done) exports.done = true console.log('a.js-2', '执行完毕') // c.js let a = require('./a.js') let b = require('./b.js') console.log('c.js-1', '执行完毕', a.done, b.done) node c.js b.js-1 false b.js-2 执行完毕 a.js-1 true a.js-2 执行完毕 c.js-1 执行完毕 true true

仔细说明一下整个过程。

在Node.js中执行c模块。此时遇到require关键字,执行a.js中所有代码。在a模块中exports之后,通过require引入了b模块,执行b模块的代码。在b模块中exports之后,又require引入了a模块,此时执行a模块的代码。a模块只执行exports.done = false这条语句。回到b模块,打印b.js-1, exports, b.js-2。b模块执行完毕。回到a模块,接着打印a.js-1, exports, b.js-2。a模块执行完毕。回到c模块,接着执行require,需要引入b模块。由于在a模块中已经引入过了,所以直接就可以输出值了。

结束。

参考:https://www.cnblogs.com/unclekeith/archive/2017/10/17/7679503.html

最新回复(0)