说说模块化规范?CommonJS和ES Module的区别?

一、常见模块化规范

1. CommonJS(CJS)

  • 主要用于 Node.js

  • 同步加载模块

  • 通过 require 和 module.exports / exports 实现

    // a.js
    module.exports = {
    name: 'test'
    }

    // b.js
    const a = require('./a')
    console.log(a.name)


2. ES Module(ESM)

  • ES6 官方标准(浏览器 & Node 都支持)

  • 使用 import / export

  • 支持静态分析(这是核心优势)

    // a.js
    export const name = 'test'

    // b.js
    import { name } from './a.js'


3. AMD(Asynchronous Module Definition)

  • 浏览器端早期方案(代表:RequireJS)

  • 异步加载

    define(['a'], function(a) {
    return a
    })


4. CMD(Common Module Definition)

  • 阿里提出(代表:SeaJS)

  • 按需加载(依赖就近)

    define(function(require, exports) {
    const a = require('./a')
    })


二、CommonJS vs ES Module 核心区别

这是面试高频重点,我帮你总结成"7大差异"👇


1️⃣ 加载机制(最重要)

CommonJS ES Module
加载方式 运行时加载 编译时加载(静态分析)
本质 动态 require 静态 import

👉 解释:

  • CommonJS:代码执行时才加载

  • ESM:编译阶段就确定依赖关系(Tree Shaking 依赖这个)


2️⃣ 是否支持 Tree Shaking

  • CommonJS ❌ 不支持

  • ES Module ✅ 支持

👉 因为 ESM 是静态结构


3️⃣ 导出值的机制(重点)

CommonJS ES Module
导出 值的拷贝 引用绑定(live binding)
示例:

CommonJS:

复制代码
let count = 0
module.exports = { count }
count++

👉 引入后是旧值


ES Module:

复制代码
export let count = 0
count++

👉 引入后是最新值(实时绑定)


4️⃣ 是否可以动态加载

CommonJS ES Module
动态加载 ✅ require ✅ import()

👉 但:

  • require 是同步

  • import() 是异步 Promise


5️⃣ this 指向

CommonJS ES Module
顶层 this 指向 module.exports undefined

6️⃣ 循环依赖处理

CommonJS ES Module
行为 返回已执行部分 更安全(引用绑定)

👉 ESM 更不容易出问题


7️⃣ 语法差异

CommonJS ES Module
导入 require() import
导出 module.exports export

三、总结一句话(面试用)

👉 可以直接背这个:

CommonJS 是运行时同步加载,导出的是值的拷贝;

ES Module 是编译时静态加载,导出的是引用绑定,支持 Tree Shaking 和更好的优化。


四、结合你前端经验(加分理解)

你现在用的:

  • React / Vue / Vite / Webpack

其实底层:

  • 打包工具(如 Vite、Webpack)都会优先解析 ES Module

  • 因为:

    • 可以 Tree Shaking

    • 可以做代码分割(Code Splitting)


五、再补一个容易被问的点

Node.js 中如何区分 CJS 和 ESM?

复制代码
{
  "type": "module"
}
  • "module" → 使用 ES Module

  • "commonjs"(默认)→ 使用 CommonJS

相关推荐
guslegend7 分钟前
脚手架原理与本地调试:从 bin 软链接到 npm link
前端·npm·node.js·脚手架·前端工程化
小宋102114 分钟前
A2UI从零实战:Agent安全生成交互界面与事件回传
javascript·人工智能·安全·交互
大包子40 分钟前
structuredClone vs lodash.cloneDeep:核心差异与选型指南
javascript·vue.js
海码事务所40 分钟前
Google Play 新个人开发者账号上架指南:12 人连续 14 天封闭测试怎么做?
前端
田威AI44 分钟前
图片内文字翻译的规格:输入输出、保真、自动化、时间与费用
前端·计算机视觉
不可能片场1 小时前
命令行中文变问号 我用环境变量救了场
前端·electron
lerhxx1 小时前
AI 应用中的上下文管理 —— 从"上下文窗口"到"分层压缩"的工程实践
前端·javascript
骑着蜗牛撵大象3271 小时前
多 Agent 分治协作:MapReduce 模式下的并行扇出与结果归并
前端
用户55318297321 小时前
Flutter iOS 热更新深入 Dart VM:读懂函数入口、解释执行与调用桥接
前端
前端snow1 小时前
为什么大厂要用Postgres + mogodb的框架?
前端