JS 中的 import 与 export
模块
模块就是实现特定功能的一组方法。
理想情况下,开发者只需要实现核心的业务逻辑,其他都可以加载别人已经写好的模块。但是,JavaScript 不是一种模块化编程语言,在 ES6 以前,它是不支持类,所以也就没有模块了。
JavaScript 社区做了很多努力,在现有的运行环境中,实现”模块”的效果。
原始写法
只要把不同的函数(以及记录状态的变量)简单地放在一起,就算是一个模块。
function f1(){//...
}
function f2(){//...
}
上面的函数 f1() 和 f2(),组成一个模块。使用的时候,直接调用就行了。
缺点:污染全局变量,无法保证不与其他模块发生变量名冲突,而且模块成员之间看不出直接关系。
对象写法
为了解决上面的缺点,可以把模块写成一个对象,所有的模块成员都放到这个对象里面。
var module1 = new Object({num: 0,f1: function (){//...},f2: function (){//...}
});
上面的函数 f1() 和 f2(),都封装在 module1 对象里。使用的时候,调用这个对象的属性
module1.f1()
这样的写法会暴露所有模块成员,内部状态可以被外部改写。比如,外部代码可以直接改变内部计数器的值。
module1.num = 1
立即执行函数写法
使用立即执行函数,可以达到不暴露私有成员的目的
var module2 = (function() {var num = 0;
var f1 = function() {alert(num)
}
var f2 = function() {alert(num + 1)
}
return {f1: f1,f2: f2
}
})()
使用上面的写法,外部代码无法读取内部的 num 变量。
console.log(module2.num) //undefined
主流模块规范
CommonJS
CMD
AMD
现阶段的标准
ES6 标准发布后,module 成为标准,标准使用是以 export 指令导出接口,以 import 引入模块,但是在 node 模块中,我们依然采用的是 CommonJS 规范,使用 require 引入模块,使用 module.exports 导出接口。
export 导出模块
export 语法声明用于导出函数、对象、指定文件(或模块)的原始值。
export 有两种模块导出方式:命名式导出(名称导出)和默认导出(定义式导出),命名式导出每个模块可以多个,而默认导出每个模块仅一个。
export { name1, name2};
export { a1 as name1, a2 as name2 };
export let name1, name2;
export let name1 = a1, name2 = a1;export default expression;
export default function (a) { console.log(a) }
export default function f1(a) { console.log(a) }
export { name1 as default};export * from name1;
export { name1, name2} from a1;
export { a1 as name1, a2 as name2 } from b;
- name1 ,name2 ,导出的标识符。导出后,可以通过这个标识符在另一个模块中使用 import 引用
- default 设置模块的默认导出。设置后import不通过标识符而直接引用默认导出
- “*” 继承模块并导出继承模块所有的方法和属性
- as 重命名导出“标识符”
- from 从已经存在的模块、脚本文件导出
命名式导出
模块可以通过 export 前缀关键词声明导出对象,导出对象可以是多个。这些导出对象用名称进行区分,称之为命名式导出。
export { fn }; // 导出一个已定义的函数
export const foo = Math.sqrt(2); // 导出一个常量
我们可以使用 * 和 from 关键字来实现的模块的继承
export * from 'article';
模块导出时,可以指定模块的导出成员。导出成员可以认为是类中的公有对象,而非导出成员可以认为是类中的私有对象:
var name = '石昊';
var age = 6;export {name, age};
// 相当于导出 {name:name, age:age}
模块导出时,我们可以使用 as 关键字对导出成员进行重命名:
var name = '石昊';
var age = 6;export {name as nickName, age};
注意,下面的语法有严重错误的情况:
// 错误演示1
export 1; // 错误演示12
var a = 100;
export a;
export在导出接口的时候,必须与模块内部的变量具有一一对应的关系。直接导出1没有任何意义,也不可能在 import 的时候有一个变量与之对应.
export a 虽然看上去成立,但是 a 的值是一个数字,根本无法完成解构,因此必须写成 export {a} 的形式。即使a被赋值为一个 function,也是不允许的。而且,大部分风格都建议,模块中最好在末尾用一个export导出所有的接口,例如:
export {f1 as default,a,b,c};
默认导出
默认导出也被称做定义式导出。命名式导出可以导出多个值,但在在 import 引用时,也要使用相同的名称来引用相应的值。而默认导出每个导出只有一个单一值,这个输出可以是一个函数、类或其它类型的值,这样在模块 import 导入时也会很容易引用。
export default function() {}; // 可以导出一个函数
export default class(){}; // 也可以出一个类
命名式导出与默认导出
默认导出可以理解为另一种形式的命名式导出,默认导出可以认为是使用了 default 名称的命名式导出。
下面两种导出方式是等价的:
const name = '石昊';
export default name;
export { name as default };
export 使用示例
使用名称导出一个模块时:
// "info.js" 模块
export function getName(name) {if(name === '唐三'){return '海神'}else if(name == '千仞雪'){return '天使神'}else if(name == '比比东'){return '罗刹神'}else{return '酱油'}
}
const weapon = '海神三叉戟';
export { weapon };
在另一个模块(脚本文件)中,我们可以像下面这样引用:
import { getName, weapon } from 'info';
console.log(getGodName("比比东")); // 罗刹神
console.log(weapon); // 海神三叉戟
使用默认导出一个模块时:
// "info.js"模块
export default function(name) {if(name === '唐三'){return '海神'}else if(name == '千仞雪'){return '天使神'}else if(name == '比比东'){return '罗刹神'}else{return '酱油'}
}
在另一个模块(脚本文件)中,我们可以像下面这样引用,相对名称导出来说使用更为简单:
// 引用 "info.js"模块
import getName from 'info';
console.log(getName("唐三")); // 海神
import 导入模块
import 语法用于从已导出的模块、脚本中导入函数、对象、指定文件(或模块)的原始值。
import 模块导入与 export 模块导出功能相对应,也存在两种模块导入方式:命名式导入(名称导入)和默认导入(定义式导入)。
import 的语法跟 require 不同,而且 import 必须放在文件的最开始,且前面不允许有其他逻辑代码,这和其他所有编程语言风格一致。
import defaultMember from "module-name";
import * as name from "module-name";
import { member1 } from "module-name";
import { member as alias } from "module-name";
import { member1 , member2 } from "module-name";
import { member1 , member2 as alias2 , [...] } from "module-name";
import defaultMember, { member1 [ , [...] ] } from "module-name";
import defaultMember, * as name from "module-name";
import "module-name";
- defaultMember 导入默认导出成员
- name 从将要导入模块中收到的导出值的名称
- member1,member1 导入指定名称的多个成员
- alias 别名,对指定导入成员进行的重命名
- module-name 要导入的模块,是一个文件名
- as 重命名导入成员名称
- from 从已经存在的模块、脚本文件等导入
命名式导入
我们可以通过指定名称,就是将这些成员插入到当作用域中。导入时,可以导入单个成员或多个成员:
// 花括号里面的变量与 export 后面的变量一一对应
import { member } from "my-module";
import { name, age } from "my-module";
通过 * 符号,我们可以导入模块中的全部属性和方法。当导入模块全部导出内容时,就是将导出模块所有的导出绑定内容,插入到当前模块的作用域中:
import * as myModule from "my-module";
// myModule 可以访问到"my-module"所有的导出绑定内容
导入模块对象时,也可以使用as对导入成员重命名,以方便在当前模块内使用:
import {reallyReallyLongModuleMemberName as shortName} from "my-module";
导入多个成员时,同样可以使用别名:
import {reallyReallyLongModuleMemberName1 as shortName1, reallyReallyLongModuleMemberName2 as shortName2} from "my-module";
导入一个模块,但不进行任何绑定:
import "my-module";
默认导入
在模块导出时,可能会存在默认导出。同样的,在导入时可以使用import指令导出这些默认值。
直接导入默认值:
import myDefault from "my-module";
也可以在命名式导入中,同时使用默认导入:
import myDefault, * as myModule from "my-module"; // myModule 做为命名空间使用
import myDefault, {foo, bar} from "my-module"; // 指定成员导入
import 使用示例
// 导出文件 a.js
function getData(url, callback) {let xhr = new XMLHttpRequest();xhr.onload = function () {callback(this.responseText)};xhr.open("GET", url, true);xhr.send();
}export function getUserInfo(url, callback) {getData(url, data => callback(JSON.parse(data)));
}// 导入文件 b.js
import { getUserInfo } from "b";
getUserInfo("http://baidu.com", data => {console.log(data);
}
default 关键字
// a.js
export default function() {}// 等效于
function a() {};
export {a as default};
在import的时候,可以这样用:
import a from './a';// 等效于
import {default as a} from './d';
这个语法糖的好处就是import的时候,可以省去花括号{},简单的说,如果import的时候,你发现某个变量没有花括号括起来(没有*号),那么你在脑海中应该把它还原成有花括号的as语法。
import $,{ each, map } from 'jquery';
// import 后面第一个 $ 是 {defalut as $} 的替代写法
as 关键字
as简单的说就是取一个别名 export 和 import 中都可以使用:
// a.js
var a = function() {};
export {a as fun};// b.js
import {fun as a} from './a';
a();
上面这段代码,export 的时候,对外提供的接口是 fun,它是a.js 内部 a 这个函数的别名。
import 中的 as 就很简单,就是你在使用模块里面的方法的时候,给这个方法取一个别名,好在当前的文件里面使用。之所以是这样,是因为有的时候不同的两个模块可能通过相同的接口,比如有一个c.js也通过了fun这个接口:
// c.js
export function fun() {};
如果在 b.js 中同时使用 a 和 c 这两个模块,就必须想办法解决接口重名的问题,as 就解决了。
JS 中的 import 与 export相关推荐
- vue滚动条禁止_vue.js中实现禁止浏览器滚动方法
大家好,本次在开发项目中,点击按钮,弹出一个自定义的弹出窗口和遮罩层,因为页面的超出一屏,有滚动条,但是想让弹出窗时候,禁止浏览器滚动,那么就简单写一个方法给大家. 思路是这样的,当弹窗弹出时候,让b ...
- import export php,import与export在node.js中的使用方法
import与export是es6中模块化的导入与导出,node.js现阶段不支持,需要通过babel进行编译,使其变成node.js的模块化代码.(关于node.js模块,可参考其他node.js模 ...
- 使用es6中import和export报错
在学习import和export时,写了一个小demo进行测试 //index.html<script> import test from './test.js' test() </ ...
- 彻底搞清楚javascript中的require、import和export
为什么有模块概念 理想情况下,开发者只需要实现核心的业务逻辑,其他都可以加载别人已经写好的模块. 但是,Javascript不是一种模块化编程语言,在es6以前,它是不支持"类"( ...
- js中export的问题
在JS中 定义一个函数名字是export 会报错(ff不报错,ie会),修改成其他名字就行了. 原因是,export是ECMA为将来保留的词(Words reserved for ECMA exten ...
- import和export在浏览器中的使用方式
import和export在浏览器中的使用方式 一般情况下,import 和 export 的使用通常是在 webpack.Vite 等构建工具中已模块的形式使用,而想在浏览器中直接使用,则需要通过一 ...
- JS的export , export default,import,export(导出js)和import(引入js)完整用法
A.规范文件名 我们确定我们有一个文件是common.js 这个文件在根目录的static文件夹下 路径如下 |-根目录/static/common.js export(导出)和import(引入) ...
- JS中export怎么用
一.export 用法 有两种不同的导出方式:命名导出和默认导出.命名导出可以导出多个接口,而默认导出,只能导出一个. 1.命名导出: 导入时,必须使用导出接口的名字. // 导出事先定义的特性 ex ...
- js模块化:require、import和export
前言 编写js模块必须要搞懂import和export的关系 Google Chrome 84.0.4147.135 (正式版本) (64 位) (cohort: Stable Installs On ...
最新文章
- 关于Android studio run 按钮灰色无法运行的总结
- HIVE 一行转多行输出办法
- 淘汰率最高的腾讯产品面试题
- Windows下的PHP开发环境搭建——PHP线程安全与非线程安全、Apache版本选择,及详解五种...
- Git拉取指定远程分支
- 推荐阅读20100708
- 欢迎清风艾艾在ITPUB博客安家!
- 游戏技能一:激光扫射的实现【CocosCreator 2D】【TypeScript】
- oppo开启系统更新服务器,oppo手机系统升级开不了机怎么办
- 让你久等了《开源安全运维平台OSSIM疑难解析--入门篇》正式出版
- Oracle数据库update语句用法,多表批量更新对应的字段值
- 深度学习的不确定性(Uncertainty/confidence score)与校准(Calibration)
- Java程序设计(2021春)——第三章类的重用笔记与思考
- 下载yahoo股票历史数据
- 计算机实验楼应用需求分析,校园网络信息化需求分析报告
- echarts+bmap地图去掉底图可点功能
- 这竟然不是阿汤哥?这个「真的吓人」视频火爆全网
- ExoPlayer的缓存 三 SimpleCache的使用
- go reflect Elem() 深入学习
- oracle vault 权限,详说Oracle Vault——原理、安装与配置