• ES6之模块化导入导出


    1、概述

    在js的历史上一直没有模块(module)体系,无法将一个大程序拆分成相互依赖的小文件,再用简单的方法拼装起来,这对开发大型的、复杂的项目形成了巨大障碍。

    在 ES6 之前,社区制定了一些模块加载方案,最主要的有 CommonJSAMD 两种。前者用于服务器,后者用于浏览器。ES6 在语言标准的层面上,实现了模块功能,

    而且实现得相当简单,完全可以取代 CommonJS 和 AMD 规范,成为浏览器和服务器通用的模块解决方案。

    2、ES6 模块(module)的设计思想是什么?

    那就是尽量的静态化,使得编译时就能确定依赖关系

    3、CommonJS模块 和 ES6 模块比较

    看两段代码

    // 导出 node 文件系统的几个方法
    let {stat,exists,readFile} = require('fs');

    注意:这段代码实际上是加载了整个 fs 模块。这种加载方式称为“运行时加载”,因为只有运行时才能得到这个对象。导致完全没办法在编译时做“静态优化”。
    // ES6 模块
    import {stat,exists,readFile} from 'fs'

    注意:这段代码只导出了三个方法,其他的方法没有加载。这种方式称为“编译时加载”,ES6可以在编译时就完成模块加载,效率要比CommonJS模块的加载方式高。  

    4、模块功能命令之 export 和 import。

    模块功能主要有两个命令构成:export 和 import。 export 命令用于规定模块的对外接口,import命令用于输入其他模块提供的功能。

    一个js文件就是一个模块,该文件内部的所有变量,外部无法获取,如果你希望外部能够读取模块内部某个变量,就必须使用export关键字输出该变量。

    输出变量:

    //eg:对外部输出三个变量----》声明后输出
    // js 文件内部 export var name = 'zjl' export var age = 18 export var gender = '男'
    // eg:对外输出三个变量-----》先声明再输出   优先使用这种写法
    
    var name = 'zjl'
    var age = 18
    var gender = '男'
    export {name,age,gender}

     输出函数:

    export function test(x,y){
       return x*y;          
    }

    export 输出的变量或函数都有自己的名字,我们也可以重命名:

    function test(){...}
    function test2(){....}
    function test3(){...}
    
    export {test as fun1,test2 as fun2,test3 as fun3}

    注意:export 命令规定的是对外接口,接口名与模块内部变量之间,必须与模块的变量建立一一对应关系。(有种键值对的意思),

    简单来说导出的变量他必须有一个值。

    export 语句不能放在代码块内,如函数内,否则会报错。因为此做法使其无法做到静态化,违背了 ES6 模块的设计理念。 

    import 命令

    通过 export 定义了模块的接口之后,我们可以通过import 命令加载这个模块。

    载入模块方式:

    // 大括号内的变量名,必须跟 export 对外接口的变量名一致
    import {name,age,gender}  from './XXX.js'
    // 重命名
    iport {name as username};

    注意几个 import 关键点

    ①import 导入的值都是只读的,不允许修改输入的接口。

    ②可以修改导入的对象 ,可以修改导入对象的属性,但不推荐这样做,建议把导入的变量(不管是普通变量还是对象)都当做只读的。

    ③import.....from 中 from 后面的路径可以是绝路径也可以是相对路径。

    ④js模块导入时可以省略后面 的 .js后缀。

    ⑤import 命令具有提升效果,它会把import命令提升到模块的头部,首先执行。

    ⑥执行同一个import命令多次,默认只会执行一次,不会执行多次

    import {name} from './XXX.js'
    import {name} from './XXX.js'
    //只会执行一次

    ⑦从同一个模块通过多条import加载不同变量,但它们对应的是同一个模块实例。import语句是 单例模式(Singleton)

    import {name}  from './a.js'
    import {age}  from 'a.js'
    // 单例模式

    ⑧不推荐 import 和 require 在同一个模块使用,因为他们的执行时期不一样,导致的结果可能就不一样。

    目前在模块中使用 require 还需要 Babel 转换比较麻烦。

    ⑨整体加载模块

    import *  as user from './a.js'
    // 导出 a 模块的所有值并命名为 user(一个对象)

    5、模块功能命令之 export default 

    我们通过前面了解到 import 导入 export 对外接口 需要知道对外接口的准确名称,才能拿到对应的值,这样是比较麻烦的。为此ES6还提供了 export default 命令,

    使用 export default 导出的值,import导入可以为这个导出值自定义名称。

    // 导出模块 a.js,导出一个匿名函数
    export default function (){...}
    
    //导入模块 b.js,  
    import fun  from './a.js';    // fun还可以为其他合法的名称

    默认输出(export default)注意点:

    ①export default 只能使用一次,export可以使用多次

    ②后面不能跟变量声明语句

    export  default var a=10; // 写法错误

    ③export default a 的含义就是jiang将变量 a 的值赋给变量 default,所以上面那种写法是错误的。

    ④ export 导出一定要指定对外接口 而 export default 不需要。

    ⑤export 和 export default 能一起使用。

    6、export 和 import 的复合写法。

    export {name,age} from 'a.js' // 这种写法相当于转发了这两个接口,没有实际导入当前模块,当前模块不能直接使用这两个变量。
    
    // 可以写成两句,实际导入当前模块
    import {name,age} from 'a.js'
    export {name,age};

    7、介绍到此结束。

  • 相关阅读:
    RabbitMQ系列教程之一:我们从最简单的事情开始!Hello World(转载)
    如何安装和配置RabbitMQ(转载)
    C++学习笔记-模板
    C++学习笔记-多态的实现原理
    C++学习笔记-多态的实现原理
    C++学习笔记-多态
    C++学习笔记-多态
    C++学习笔记-继承中的构造与析构
    C++学习笔记-继承
    C++学习笔记-封装
  • 原文地址:https://www.cnblogs.com/zjl-712/p/11432787.html
Copyright © 2020-2023  润新知