失眠网,内容丰富有趣,生活中的好帮手!
失眠网 > JS JavaScript模块化(ES Module/CommonJS/AMD/CMD)

JS JavaScript模块化(ES Module/CommonJS/AMD/CMD)

时间:2020-12-15 17:25:11

相关推荐

JS JavaScript模块化(ES Module/CommonJS/AMD/CMD)

前言

前端开发中,起初只要在script标签中嵌入几十上百行代码就能实现一些基本的交互效果,后来js得到重视,应用也广泛起来了,

jQuery,Ajax,Node.Js,MVC,MVVM等的助力也使得前端开发得到重视,也使得前端项目越来越复杂,

然而,JavaScript却没有为组织代码提供任何明显帮助,甚至没有类的概念,更不用说模块(module)了,那么什么是模块呢?

一个模块就是实现特定功能的文件,有了模块,我们就可以更方便地使用别人的代码,想要什么功能,就加载什么模块。

一、AMD 规范

AMD 是RequireJS在推广过程中对模块定义的规范化产出。

模块将被异步加载,模块加载不影响后面语句的运行。

所有依赖某些模块的语句均放置在回调函数中。

用法:

定义模块:define(id?, dependencies?, factory)加载模块:require([module], factory)

// a.js// 依赖有三个默认的,即"require", "exports", "module"。顺序个数均可视情况// 如果忽略则factory默认此三个传入参数// id一般是不传的,默认是文件名define(["b", "require", "exports"], function(b, require, exports) {console.log("a.js执行");console.log(b);// 暴露api可以使用exports、module.exports、returnexports.a = function() {return require("b");}})// b.jsdefine(function() {console.log('b.js执行');console.log(require);console.log(exports);console.log(module);return 'b';})// index.js// 支持Modules/Wrappings写法,注意dependencies得是空的,且factory参数不可空define(function(require, exports, module) {console.log('index.js执行');var a = require('a');var b = require('b');})// index.jsrequire(['a', 'b'], function(a, b) {console.log('index.js执行');})

二、CMD 规范

CMD 是SeaJS在推广过程中对模块定义的规范化产出。

在 CMD 规范中,一个模块就是一个文件。

用法:

定义模块:define(factory)

/ require, exports, module参数顺序不可乱// 暴露api方法可以使用exports、module.exports、return// 与requirejs不同的是,若是未暴露,则返回{},requirejs返回undefineddefine(function(require, exports, module) {console.log('a.js执行');console.log(require);console.log(exports);console.log(module);})// b.js// define(function(require, module, exports) {console.log('b.js执行');console.log(require);console.log(exports);console.log(module);})// index.jsdefine(function(require) {var a = require('a');var b = require('b');console.log(a);console.log(b);})

三、CommonJs规范

CommonJs 是服务器端模块的规范。

Node.js 采用了这个规范。Node.JS首先采用了js模块化的概念。

根据 CommonJs规范,一个单独的文件就是一个模块。每一个模块都是一个单独的作用域,也就是说,在该模块内部定义的变量,无法被其他模块读取,除非定义为 global 对象的属性。

用法:

输出模块:module.exports加载模块:require

// 导出使用module.exports,也可以exports。exports指向module.exports;即exports = module.exports// 就是在此对象上挂属性// commonjsmodule.exports.add = function add(params) {return ++params;}exports.sub = function sub(params) {return --params;}// 加载模块使用require('xxx')。相对、绝对路径均可。默认引用js,可以不写.js后缀// index.jsvar common = require('./commonjs');console.log(common.sub(1));console.log(common.add(1));

四、ES Module

ES6 在语言标准的层面上,实现了模块功能,成为浏览器和服务器通用的模块解决方案,完全可以取代 CommonJS 和 AMD 规范。

基本特点:

每一个模块只加载一次, 每一个JS只执行一次, 如果下次再去加载同目录下同文件,直接从内存中读取;每一个模块内声明的变量都是局部变量, 不会污染全局作用域;模块内部的变量或者函数可以通过export导出;一个模块可以导入别的模块

用法:

输出模块:export加载模块:import

// moduleexport function fn1(){return "这是 fn1";}export function fn2(){return "这是 fn2" ;}// main.js//逐一加载import { fn1, fn2 } from './module';console.log( fn1());console.log( fn2());//整体加载import * as all from './module';console.log( all.fn1() );console.log( all.fn2() );

动态加载模块:

// 普通写法import('./module').then(({ a }) => {})// async、awaitconst { a } = await import('./module');

五、各模块之间的区别

1、CommonJS 与 AMD/CMD 的差异

CommonJS:是同步加载(代码在本地,加载时间基本等于硬盘读取时间)。AMD / CMD:是异步加载

2、AMD 与 CMD 的差异

AMD是提前执行,CMD是延迟执行AMD推荐依赖前置,CMD推荐依赖就近

3、CommonJS 与 ES Module 的差异

CommonJS 模块是对象,是运行时加载,运行时才把模块挂载在 exports 之上(加载整个模块的所有),加载模块其实就是查找对象属性ES Module 不是对象,是使用 export 显示指定输出,再通过 import 输入,此法为编译时加载CommonJS 模块输出的是一个值的拷贝,ES6 模块输出的是值的引用。CommonJS 模块是运行时加载,ES6 模块是编译时输出接口

3、各模块用法上的区别

详见各模块介绍...

随笔整理自
/p/da2ac9ad2960
感谢博主分享!

如果觉得《JS JavaScript模块化(ES Module/CommonJS/AMD/CMD)》对你有帮助,请点赞、收藏,并留下你的观点哦!

本内容不代表本网观点和政治立场,如有侵犯你的权益请联系我们处理。
网友评论
网友评论仅供其表达个人看法,并不表明网站立场。