(一)首先平常是怎么引入文件的
(二)据了解没有模块化概念之前, js在项目开发当中, 站的地位非常低
- 在ie6之前, 是没有js引擎的, 当时js应该在渲染引擎中, 在当时写一点js代码, 浏览器就直接崩溃了
- ie6之后出来了javascript引擎, 就是单独列出了一个 js 的解释器, 当时的写法是
<script type="text/javascript">
..xxxx...
<script>
- 浏览器后来发展功能加多, js代码加多, 这种写法不行了, 页面会写一堆js, 不好维护, 这是就用了开始的方法, 所有的逻辑放到一个文件中去维护, 然后只引入这一个文件
(三)随着前端的技术增加, 异步 ajax cookie..... js的代码会越来越多
- 开始我们说所有逻辑都放到一个js中, 但是如果多个页面呢? 每个页面都需要引入一次, 那不是重复引入吗
- 所以就想到了, 一个页面使用一个js去维护, (以页面为思想 分模块 分js文件)但是还是不合理
- 想到通过程序来划分模块, 那个页面用到这个程序就引入这个程序
(四)问题出现了
- 引入很多程序时就会出现
- 污染全局 --> 变量重名 --> 变量覆盖
- 文件相互依赖, 顺序不对时, 就会报错
- 那么模块化解决的问题就是:
- 加载顺序
- 污染全局
(五)所以我们在解决模块化文件就想到创建作用域, 谁创建作用域就是函数
- 这里我们想就会创建一个命名函数, 然后调用它, 将逻辑写到函数中
- 但是这样麻烦, 就想到用立即执行函数
- 我们将它放在作用域中, 但是需要在外部拿到数据, 就需要return 并且需要写成对象, 这样就可以导出很多数据
- 这样是解决了 , 但是, 看到这里是依赖b的, 所以就有了, 将每个模块抛出的东西去接收 模块A:
模块B:
- 这里看到就是模块的注入
- 解决了污染全局
- 模块之间独立并且相互依赖
5. 但是我么在es5的方法中, 依然没有解决引入顺序不对就会报错的问题
(六)讨论到目前就是使用立即执行函数做模块化, 使用的是javascript语法本身去实现 [模块化, 插件化]
(七)之后Nodejs诞生, 带来了前所未有的模块化体验 叫 CommonJs
CommonJs -> 不是js, 是规范 -> 他不是js的方法, 集合, 库, 也不是框架, 就是一种规范 -> 来源于nodeJs -> 他是同步进行的
- require('....') 引入模块
- mdule.exports 导出模块
到这里我们不再依赖html页面, 我们依赖的是真正js实现模块化 但是他运行于node环境上
(八)客户端 的 "CommonJS" === AMD
Asynchronous Module Definition 异步模块定义
- define(moudleName模块名, [module] 需要依赖的模块, factory工厂函里面写); // 定义模块
- require([module], callback); // 引入模块
其实AMD, 浏览器也是不支持的, 是通过 require.js 实现的
模块A
模块B
- index.js 配置 require.config 文件路径, 他不会像node中自动寻找文件
- 前面所有模块加载完毕才执行回调函数, 这也叫前置依赖
- 一个模块的回调函数的执行, 必须依赖前面的模块的执行完毕, 也就是前置依赖
html引入
看控制台发现了引入模块通过async实现异步加载
CMD - 他是阿里为模块化做的贡献
Common Module Definition 通用模块定义
- define(function (require, export, module) {}); 定义模块
- seajs.use([module路径], function (moduleA, moduleB, moduleC) {}); 使用模块
CMD 和 AMD 的区别
- AMD 导入先加载模块, 依赖前置(不懂看上面)
- CMD 依赖就近 按需加载, 虽然引入写在前面, 但是什么时候用到了他才会加载
ES6模块化
ES6 和 commonJS 的区别 不同点
导出
es6导入
commonJS导入
通过结果看出, 不同点
(1)
- commonJS 模块输出的是一个值的拷贝
- ES6 输出的是值的引用
(2)
- commonJS模块是在运行时加载(因为commomJS是运行在服务端的, 程序编译后, 当正式运行时遇到require函数才会加载)
- es6模块是在编译时加载(es6是载编译时模块就已经存在了)