// a.jsvar name = 'morrain'var age = 18exports.name = nameexports.getAge = function(){return age}// b.jsvar a = require('a.js')console.log(a.name) // 'morrain'a.name = 'rename'var b = require('a.js')console.log(b.name) // 'rename'- 模块输出的结果是值的拷贝,一但输出,模块内部变化后,无法影响之前的引用,而ESModule是引用拷贝
// a.jsvar name = 'morrain'var age = 18exports.name = nameexports.age = ageexports.setAge = function(a){age = a}// b.jsvar a = require('a.js')console.log(a.age) // 18a.setAge(19)console.log(a.age) // 18- cjs在运行时加载,ESM是编译时加载
- 缺点:不支持异步
- cjs更偏向于服务端,因为服务端I/O能力强,所以CMJ是同步的方法
- ESM时机遇编译时的,所以支持异步能力
经典代表:require.js
使用方法:
// define来定义模块define(id, [depends], callback);// require进行加载require([module], callback);示例://提前加载执行顺序// RequireJSdefine('a', function () {console.log('a load')return {run: function () { console.log('a run') }}})define('b', function () {console.log('b load')return {run: function () { console.log('b run') }}})require(['a', 'b'], function (a, b) {console.log('main run') //a.run()b.run()})// a load// b load// main run// a run// b run缺点:- 在代码运行时,会先递归的找出所有的依赖,然后将依赖放到前面加载
- 如果依赖过多,项目可能会变慢,引入成本升高
- 如果现在AMD中兼容CJS的代码怎么办?
define('amdModule', [], require => {const dep1 = require('./dep1');const dep2 = require('./dep2');// 业务逻辑……})5.CMDCMD(Common Module Definition-通用模块定义)推崇依赖后置,也就是按需执行 CMD解决了AMD依赖前置导致的引入成本过高的问题 整合了CJS和AMD的特点,浏览器端运行经典代表:Sea.js
// 引入requirevar fs = require('fs'); //同步require.async('./module3', function (m3) {}) //异步// sea.js,按需引入define('a', function (require, exports, module) {console.log('a load')exports.run = function () { console.log('a run') }})define('b', function (require, exports, module) {console.log('b load')exports.run = function () { console.log('b run') }})define('main', function (require, exports, module) {console.log('main run')var a = require('a')a.run()var b = require('b')b.run()})seajs.use('main')// main run// a load// a run// b load// b run缺点:- 依赖打包,加载逻辑存在于每个模块中
- 扩大了模块体积,同时功能上依赖编译
(function(root, factory) {if (typeof module === 'object' && typeof module.exports === 'object') {console.log('是commonjs模块规范,nodejs环境')module.exports = factory();} else if (typeof define === 'function' && define.amd) {console.log('是AMD模块规范,如require.js')define(factory)} else if (typeof define === 'function' && define.cmd) {console.log('是CMD模块规范,如sea.js')define(function(require, exports, module) {module.exports = factory()})} else {console.log('没有模块环境,直接挂载在全局对象上')root.umdModule = factory();}}(this, function() {return {name: '我是一个umd模块'}}))7.ESMESModule是伴随着ES6推出的原生模块化解决方案 import输入、export输出- 支持异步加载
- 编译时加载,支持静态分析
- 更好的支持chunk和tree shaking
- 支持动态导入(按需加载)import().then()
- 支持import.meta获取模块元数据
推荐阅读
- 看完这篇文章,你就是最了解普洱茶的人
- 木耳没泡开能吃吗
- 奇瑞电动车多少钱一辆 奇瑞电动车
- 一文搞懂802.1x协议,认证逃生方案的核心技术
- 一米装饰 随意居装饰
- 高档四件套床上用品图片 女人床上用品
- 快速了解金属天花吊顶安装安全和装饰 金属屋面瓦
- 钱币|辽代铸造的下八品钱币,是哪八品,关于辽代钱币铸造你了解多少?
- 一文带你搞懂 Mmap 技术
- 张若昀|曝当红男星多次出轨L姓女星,原配全了解却忍让,选择共享老公!
