AMD、CMD、CommonJS、ESM 差异
1. 一句话定位
- CommonJS :Node 服务端模块化,同步加载
- AMD :浏览器模块化,RequireJS,提前加载、并行执行
- CMD :浏览器模块化,SeaJS,就近加载、延迟执行
- ESM :ES 官方标准,静态编译、现代唯一主流
2. 核心差异对比表(面试必背)
| 特性 |
CommonJS |
AMD |
CMD |
ESM |
| 全称 |
CommonJS |
Asynchronous Module Definition |
Common Module Definition |
ES Module |
| 代表 |
Node.js |
RequireJS |
SeaJS |
浏览器 / 现代构建工具 |
| 加载方式 |
同步 |
异步 |
异步 |
静态 / 异步 |
| 依赖执行时机 |
运行时 |
提前加载、提前执行 |
就近 require、延迟执行 |
编译时确定 |
| 导出方式 |
module.exports |
define |
define |
export / export default |
| 导入方式 |
require() |
define([...]) |
require() |
import |
| 支持 Tree Shaking |
❌ 不支持 |
❌ 不支持 |
❌ 不支持 |
✅ 支持 |
| 取值方式 |
值拷贝 |
引用 |
引用 |
引用(动态绑定) |
| 现在地位 |
Node 仍在用 |
已淘汰 |
已淘汰 |
现代标准 |
3. 逐一看区别(面试口语版)
CommonJS(Node)
- 同步加载,不适合浏览器(会阻塞渲染)
require() 导入,module.exports 导出
- 导出是值拷贝,导出后外部改不影响内部
- 不支持 Tree Shaking
- 仅用于 Node,浏览器不原生支持
AMD(RequireJS)
- 浏览器异步模块化
- 依赖前置:一开始就把所有依赖加载并执行
- 写法:
js
复制代码
define(['a', 'b'], function(a, b) {
return {}
})
CMD(SeaJS)
- 浏览器异步模块化
- 依赖就近 :用到时再
require
- 延迟执行
js
复制代码
define(function(require, exports, module) {
const a = require('./a')
})
ESM(ES Module,现在唯一标准)
- 官方标准,浏览器 & Node & 构建工具全支持
import / export 静态语法
- 编译时加载,能 Tree Shaking
- 导出是引用传递,实时更新
- 支持顶层 await
- 未来唯一方案
4. 最经典两道面试题答案
AMD vs CMD 区别?
- AMD:依赖前置,提前执行
- CMD:依赖就近,延迟执行
CommonJS vs ESM 区别?(必考)
- CommonJS 是运行时加载 ,ESM 是编译时静态加载
- CommonJS 同步,ESM 可异步
- CommonJS 值拷贝 ,ESM 引用传递
- CommonJS 不支持 Tree Shaking,ESM 支持
- CommonJS 顶层
this 是 module,ESM 是 undefined
- CommonJS 不能用
import/export,ESM 不能用 require