ES6 新特性梳理系列丨Module

本文介绍了ES6的模块化特性,包括export和import命令的使用,以及默认导出和整体加载的概念。通过export,模块可以导出多个变量或函数,import则用于导入这些导出的内容。export default命令允许创建默认导出,使得导入时无需知道具体的导出名称。模块化是ES6提升开发效率和代码组织的重要特性。
摘要由CSDN通过智能技术生成

ES6 新特性梳理系列文章将在本号持续发布,一起查漏补缺学个痛快!若您有遇到其它相关问题,非常欢迎在评论中留言讨论,达到帮助更多人的目的。若感本文对您有所帮助请点个赞吧!


JavaScript 与 ECMAScript

JavaScript 诞生于1995年,设计者是就职于 Netscape 公司的工程师 Brendan Eich。它是一门仅用10天就完成设计的编程语言,但至今为止已对业界保持26年的影响,且势头愈发强劲

1996年 Netscape 将 JavaScript 提交给ECMA,希望它可以成为“标准化一个通用的、跨平台的、中立于厂商的脚本语言的语法和语义标准”,1997年 ECMA 确定将 JavaScript 作为浏览器脚本语言的标准,并为之重命名为 ECMAScript,所以通常来讲我们将 ECMAScript 视为 JavaScript 的标准,而 JavaScript 则是 ECMAScript 的实现及扩展

1997年-1999年连续发布了ES1-ES3发布,2000年开始酝酿新版本的升级内容,中间因标准委员会意见未能达成一致,只做了部分功能的小范围升级及支持,于2009年12月发布了过渡版 ECMAScript 5.0,2011年6月发布 ECMAScript 5.1 并成为 ISO 国际标准

2013年3月 ECMAScript 6 草案冻结,2013年12月 ECMAScript 草案发布,2015年6月 ECMAScript 6 正式通过,成为新的国际标准。ES6 泛指自2015年升级为 ECMAScript 6.0 后的所有子版本,如:ES2015-ES2020,等同于ES6.0-ES6.5,这是 JavaScript 走向企业级编程语言的强势升级

不断升级的标准与实现,对于开发效率及产品质量起到强有力的支撑,接下来我们开始梳理ES6的新特性吧!


为什么要有 Module

和其他语言不同,对于模块化来说,JS是不支持的,我们无法将一个程序划分为很多个小文件,然后通过一定的方法将他们联系起来。

在 ES6 之前,对于模块化加载主要有 Commonjs、AMD、CMD 三种。ES6官方于 2015 年发布的 ECMA Script 2016 官方标准中,就新增了官方对于JS 模块化的支持。完全可以取代现有的 CommonJS、AMD、CMD 规范。

在介绍 Module 之前,我们要知道,在模块化编程中,所谓一个模块,就是一个文件,每个文件中存在一个文件作用域,各个文件之间互补干扰,就比如 a.js 文件里有一个变量 foo,b.js 文件里也有一个 foo,这是完全可以的,并不冲突。


export 命令

export命令用来指定当前模块的对外接口,所谓对外接口,就是外部可以访问当前模块的开放作用域,只有我 export 的变量,你才可以访问,否则,你看都看不到。

// test.js
export var name = 'hello';
export var age = 18;

上面的test.js 文件就导出了两个变量,一个 name,一个 age,此外还有另一种形式。

// test.js
var name = 'hello';
var age = 18;
export { name, age }

在 export 命令后面,使用大括号指定导出的一组变量,和前面的方式是等价的,不过推荐使用这种形式,可以在文件最后,看到当前文件所有的导出变量有哪些。

我们也可以在导出的时候,使用as关键字起别名。

// test.js
var name = 'hello';
var age = 18;
export { name as yourName, age as yourAge, age as hisAge }

上面通过 as 关键字,导出的时候重命名了 name 和 age 变量,重命名后,age 可以用不同的名字导出两次。

注意,和 CommonJS 不同,CommonJS 在导入的时候,就会立马执行导入文件中的代码,然后将得到的对象存入缓存,每次从第一次存入的缓存中拿到值,所以,当之前的文件中的变量改变时,这里并不能够拿到改变后的最新值。

export 导出的接口,与接口对应的值是动态绑定关系,也就是通过这个接口可以实时访问当前模块的最新数据,就像一个指针一样,指向模块中的内容。

//  CommonJS模块导出
// test.js   
var name = 'hello';
setTimeout(() => foo = 'world', 500);
module.exports.name = name


// CommonJS 模块导入
var name = require('./test)
console.log(name) // hello
setTimeout(() => console.log(name), 1000)  // hello   


// ES6模块导出
// test.js   
export var name = 'hello';
setTimeout(() => foo = 'world', 500);


// ES6 模块导入
import { name } from './test
console.log(name) // hello
setTimeout(() => console.log(name), 1000)  // world

import 命令

在使用了 export 命令定义了模块的对外接口后,其他的文件就可以通过 import 命令来加载这个模块,拿到对外接口。

// test.js   
export var name = 'hello';
setTimeout(() => foo = 'world', 500);


// ES6 模块导入
import { name } from './test
console.log(name) // hello

上面的 import 命令,用于加载 test.js 文件,并从中获得变量 name。import 命令接受一堆大括号,里面指定从其他模块导入的变量名。注意,大括号里面的变量名,必须与被导出模块(test.js)导出的变量名相同。

你也可以使用 as 命令,在导入时,为导入内容重新命名。

import { name as firstName } from './test';

import 后面的 from 指定模块文件的位置,可以是相对路径,也可以是绝对路径,.js 路径可以省略。


模块的整体加载


在模块导出的变量比较多的时候,我们导入的时候并不需要一个一个导入,可以使用星号(*)指定一个对象,所有的导出值都将作为这个对象的属性存在。

// test.js
export name = '张三'
export age = 18
export hobbies = '吃饭、睡觉'


// main.js
import * as all from './test'
console.log(all.name) // 张三
console.log(all.age) // 18
console.log(all.hobbies) // 吃饭、睡觉


export default 命令

在前面的例子中,我们可以看到,在 import 的时候,必须知道导出的变量名是什么,否则无法加载。那么有没有一种方法,用户无需知道导出的变量名,就可以直接导入使用呢?

这个问题的解决方案就是这里的 export default 命令,默认导出。

// test.js  默认导出是一个函数
export default function(){
  console.log('123')
}


// main.js
import fn from './test'
fn() // 123

上面代码的 import 命令可以使用任何一个变量来指向 test.js 默认导出的方法,这个时候就不需要知道 test.js 模块导出的函数名是什么了。需要注意的是,这时 import 命令后面,不使用大括号。

// test.js  默认导出是一个函数
export default function foo(){
  console.log('123')
}


// main.js
import fn from './test'
fn() // 123

export default 用在非匿名函数前面也可以,因为文件作用域的原因,foo函数名在外部是无效的加载的时候,视同匿名函数加载。

本质上,export default 输出的是一个叫做 default 的变量或方法,然后系统允许你为他重新命名。所以,下面的写法是有效的。

// test.js
function add(x, y) {
  return x + y;
}
export {add as default};
// 等同于
// export default add;


// mian.js
import { default as xxx } from './test';
// 等同于
// import xxx from './test';

ES6 新特性梳理系列文章将在本号持续发布,一起查漏补缺学个痛快!若您有遇到其它相关问题,非常欢迎在评论中留言讨论,达到帮助更多人的目的。若感本文对您有所帮助请点个赞吧!

叶阳辉

HFun 前端攻城狮

往期精彩:

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值