ThinkChat2.0新版上线,更智能更精彩,支持会话、画图、阅读、搜索等,送10W Token,即刻开启你的AI之旅 广告
JavaScript 的顶层对象是window, Node的顶层对象是global JavaScript也存在globale, 但是不对外访问,而使用window对象指向global对象 Node.js 的global.a 得不到,是模块的变量,不是全局变量 var?a?=?100; //console.log(global.a);?//undefined,global是全局 console.log(a); 在Node.js中,一个文件是一个模块,每个文件都有自己的作用域 ,使用var声明的是当前模块作用域的,而不是全局的。 Node.js 模块 1. 核心模块, Node.js提供 2. 文件模块, 用户编写 核心模块在Node源码编译过程,编译为二进制文件,在Node启动时,直接加载进内存。 文件模块运行时动态加载,需要完整的路径分析、文件定位、编译,速度较慢。 模块加载 JavaScript使用 <script>标签, Node.js使用 require()方法引入。 前端浏览器会缓存静态脚本, Node对导入的模块也会缓存,缓存的是编译和执行之后的对象 模块标识: 1. 核心模块: http、path 2. . 或 ..开始的相对路径文件模块 3. /开头的绝对路径文件模块 4. 非路径形式的文件模块 当前路径以 ./ 开头 后缀名: 后缀名可以包含,也可以不包含。 不包含则首选查找没有后缀的文件,在按.js .json .node依次查找。 .node 和 .json文件, 带上扩展名,可以加快速度。 跨模块访问变量: 1. 将变量定义到 global中, 简单、污染了全局环境,不推荐 2. 使用模块对象(Module) module.id 模块的识别符,通常是带有绝对路径的模块文件名。 module.filename 模块的文件名,带有绝对路径。 module.loaded 返回一个布尔值,表示模块是否已经完成加载。 module.parent 返回一个对象,表示调用该模块的模块。 module.children 返回一个数组,表示该模块要用到的其他模块。 module.exports 表示模块对外输出的值。 module.exports属性表示当前模块对外输出的接口,其他文件加载该模块,实际上就是读取module.exports变量 //a.js var a = 100; m module.exports.a = a; //b.js var result = require('./a'); c console.log(result);//'{ a: 100 }' 为了方便,Node为每个模块提供一个exports变量,指向module.exports。造成的结果是,在对外输出模块接口时,可以向exports对象添加方法 console.log(module.exports === exports); 模块编译: 不同的文件扩展名,载入方法不同: 1. js 文件, 通过 fs模块同步读取文件后编译执行 2. mode文件,C/C++编写的扩展文件, 通过dlopen()方法加载 3. json文件, 通过fs模块同步读取,用 JSON.parse()解析返回的结果 CommonJs、AMD、CMD、ES6模块 JavaScript 模块化 模块化好处 - 独立,维护和改动方便 - 可以重复利用 需要解决的问题: 1. 命名冲突 // a.js var a = 1; // b.js var a = 2; 2. 文件依赖 <script src='a.js' type='text/javascript'></script> <script src='b.js' type='text/javascript'></script> 如何解决冲突、依赖 1. 使用命名空间,暴露模块所有成员 let module = { name: '', hello() { console.log(this.name); } } 2. 立即执行函数+闭包 函数内部有自己独立的作用域, 外部只能访问暴露的成员 let module = (function () { let privateName = 'private'; // 私有变量 let privateFn = function () {}; // 私有函数 // 对外暴露的成员 return { name: '111', // 公有属性 hello() { // 公有方法 console.log(this.name); } } })(); 3. 立即执行函数+类 const People = (function () { let privateName = 'private'; // 私有变量 let fn = function () {}; // 私有方法 return class People { constructor () { this.name = 'likang xie'; // 公有变量 } // 公有方法 sayName() { console.log(this.name); } } })()