[js基础]ECMAScript2015(ES6)精要知识点(下)

news2024/11/27 12:37:33

模块化

模块就是在单个文件中声明的JavaScript代码。我们可以用JS代码直接从其他文件中导入函数、变量和类

在NodeJS之前,由于没有过于复杂的开发场景,前端是不存在模块化的,后端才有模块化。

NodeJS诞生之后,它使用CommonJS的模块化规范。从此,js模块化开始快速发展

CommonJS

多用module.exports定义当前模块对外输出的接口(不推荐直接用exports),用require加载模块。

// name.js
module.exports.name = 'abc'
module.exports.sayName = function() {console.log('name')}

或者

// name.js
var name = 'abc';
function sayName() {console.log('name')}
module.exports = {
  name: name,
  sayName: sayName
}

引用:[普通模块name.js]

var nameObj = require('./name.js')
console.log(nameObj.name)
nameObj.sayName(); // name

如果引用系统模块[会去node_modules里找]

var http = require('http');
http.createService(...).listen(3000);

特点:用同步的方式加载模块。

缺点:在服务端,模块文件都存放在本地磁盘,读取非常快,所以这样做不会有问题。但是在浏览器端,限于网络原因,更合理的方案是使用异步加载

AMD

AMD是一种异步模块化标准。

RequireJS是AMD最流行的实现。(CommonJS与requireJS无关,只是用了require语句

场景:项目中我们会将JS组件放到不同的文件里,并通过script标签引入。当组件间存在依赖关系的时候,被依赖的组件需要放到前面。否则的话会出现XXX is undefined或者XXXX is not a function之类的错误。比如一个jquery的插件显然是依赖jquery核心库的,所以jquery核心库文件必须先引入。当组件间依赖复杂时,使用RequireJs可以从一个根开始检查依赖,根据这些依赖关系自动的帮助我们插入script标签。

原理:所有依赖这个模块的语句,都定义在一个回调函数中,等到加载完成之后,这个回调函数才会运行。

简单使用:

引入requireJS。指定工程JS模块入口。

// index.html
<script src="lib/require.js" data-main="js/scripts/main.js"></script>

情景一: 入口文件main.js里用RequireJs映射Jquery并使用

require.config(
    {
        // baseUrl——用于加载模块的根路径
        baseUrl:'./js',
        // paths——用于映射不存在根路径下面的模块路径
        paths: {
            'Jquery': lib/jquery'
        }
    }
);
require(['Jquery'],function ($) {
    // jquery操作
     $(document).on('click','#contentBtn',function(){
        $('#messagebox').html('You have access Jquery by using require()');
     });
});

情景二:app.js需要依赖tools.js模块

// tool.js
define(function(){
    return{
        decs : 'abcd',
    };
})
//  app.js
require(['./tool'],function(data){
    console.log(data.desc)
})

define函数接收[moduleName][requireModeule][callback]三个参数。

完整写法诸如:

define('./app',['./tool'],function(data){
   .....
})

第一个参数是定义模块名,第二个参数是传入定义模块所需要的依赖,第三个函数则是定义模块的主函数,主函数和require的回调函数一样,同样是在依赖加载完以后再调用执行。

不建议传入第一个参数,即自定义模块名,因为如果哪一天我将这个文件转移到其他目录下,那我就得在这这里再修改一次模块名。官方其实也不推荐,用官方的说法是:让优化工具去自动生成这些模块名吧!

情景三:将require.config配置在入口文件,以供全局使用

// main.js
define(function(){
    require.config({
        baseUrl:'./js',
        paths: {
            'Jquery': lib/jquery'
        }
    });
}); 
// app.js
require(['./main.js'],function(){
    require(['Jquery'],function ($) {
         $(document).on('click','#btn1',function(){
            $('#messagebox').html('anc');
            require(['./tool'],function(data){
                console.log(data.desc)
            });
         });
    });
});

require.config额外配置:

shims——虽然目前已经有一部分流行的函数库(比如 jQuery)符合 AMD 规范,但还有很多库并不符合。shim 就是为了加载这些非 AMD 规范的 js,并解决其载入顺序的。

require.config({
baseUrl: './js',
paths: {
    'Jquery': lib/jquery'
}
shim: {
    'backbone': {
        deps: ['underscore', 'Jquery'],
        exports: 'Backbone'
    },
    'underscore': {
        exports: '_'
    }
},
});

我们想通过 RequireJS 来使用 backbone,那么你就需要在配置中把它定义为一个 shim。同时通过 deps 配置其依赖关系,可以保证 underscore、jquery 先被加载。

CMD

CMD是另一种js模块化方案,它与AMD很类似,不同点在于:AMD推崇依赖前置、提前执行,CMD推崇依赖就近、延迟执行。CMD最流行的实现模式便是sea.js

AMD模式:

define(["a", "b", "c", "d", "e", "f"], function(a, b, c, d, e, f) { 
    // 等于在最前面声明并初始化了要用到的所有模块
    a.do()
    if (false) {
      // 即便没用到某个模块 b,但 b 还是提前加载了。**这就CMD要优化的地方**
      b.do()
    } 
});

CMD模式:

define(function(require, exports, module) {
    var a = require('./a'); //在需要时申明
    a.doSomething();
    if (false) {
        var b = require('./b');
        b.doSomething();
    }
});

完整写法:

// index.html
<script type="text/javascript" src="js/libs/sea.js"></script>
<script type="text/javascript">
    seajs.use('./js/main.js')
</script>
// main.js
define(function(require,exports,module){
    let module1 = require('./module1.js')
    console.log(module1.getName()) // module1
 
    let module4 = require('./module4.js') //module2 module4 module3
    module4.getVal()
 
})
// modoule1
define(function(require,exports,module){
    let name = 'module1';
    function getName(){
        return name;
    }
    //暴露模块 
    module.exports = {getName}
})
// module4
define(function(require,exports,module){
    let val = 'module4'
    function getVal(){
        console.log(val)
    }
 
    // 引入module2 同步
    let module2 = require('./module2.js');
    // 执行module2
    module2()
 
    // 异步引入module3
    require.async('./module3.js',function(module3){
        //执行module3
        module3.module3.getData()
    });
 
    // 暴露模块
    module.exports = {getVal}
 }
// module2.js
define(function(require,exports,module){
    let msg = 'module2';
    function getMsg(){
        console.log(msg)
    }
    //暴露模块
    module.exports = getMsg;
})
// module3.js

define(function(require,exports,module){
    let data = 'module3'
    function getData(){
        console.log(data)
    }
 
    // 暴露模块
    exports.module3 = {getData}
})

因为在module4.js中引入了module3.js是异步的,所以先打印出module4,再打印出module3.

UMD

UMD是AMD和CommonJS的一个糅合。AMD是浏览器优先,异步加载;CommonJS是服务器优先,同步加载。

既然要通用,怎么办呢?那就先判断是否支持node.js的模块,存在就使用node.js;再判断是否支持AMD(define是否存在),存在则使用AMD的方式加载。这就是所谓的UMD。

((root, factory) => {
  if (typeof define === 'function' && define.amd) {
    //AMD
    define(['jquery'], factory);
  } else if (typeof exports === 'object') {
    //CommonJS
    var $ = requie('jquery');
    module.exports = factory($);
  } else {
    //都不是,浏览器全局定义
    root.testModule = factory(root.jQuery);
  }
})(this, ($) => {
  //do something...  这里是真正的函数体
});

ES6Module

ES2015在JavaScript标准中引入官方模块功能。

// a.js
const numberFn = r=> r * r;
const nmber = 5;
export {numberFn,number}

或者

// a.js
export const numberFn = r=> r * r;
export const nmber = 5;

使用:

import {number as count, numberFn} from './a.js' 
console.log(numberFn(count))

或者将整个模块当做一个变量来导入

import * as nn from './a.js' 
console.log(nn.numberFn(nn.number))

假设模块中只有一个成员被导出。可以使用export default关键字

// b.js
export default class Book{
    constructor(title) {
        this.title = title
    }
    printTitle()  {
        console.log(this.title)
    }
}
import Book from './b.js'
const aBook = new Book('aaa')
aBook.printTitle(); // aaa

导入export default导出模块。不需要将类名包含在花括号中(import {book} from './b.js' X)。只有模块有多个成员被导出才用花括号。

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.coloradmin.cn/o/331811.html

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈,一经查实,立即删除!

相关文章

filebrowser logo和样式自定义及免密访问

这两天接到项目一个需求&#xff0c;客户需要文件管理存储服务&#xff0c;看了下大概的功能&#xff0c;计划用源码开发的&#xff0c;但是看后期这块调整也不大&#xff0c;就采用开源的项目进行即可&#xff0c;开源项目对比后&#xff0c;发现filebrowser比较适合我&#x…

Spring如何解决循环依赖

今天面试了同程旅行&#xff0c;面试官问到了这个问题&#xff0c;所以今天来总结学习一下 Spring是如何解决循环依赖问题&#xff1f; 前言 Spring的依赖注入分为 setter注入和 构造器注入 这里说的解决循环依赖主要指的是&#xff1a;单例模式下的setter循环依赖 如果是&a…

ThreadLocal使用与原理

目录一、ThreadLocal1.ThreadLocal简介1.1 是什么2.能干嘛1.3 api介绍1.4 实战1.5 通过上面代码总结2.从阿里ThreadLocal规范开始3.ThreadLocal源码分析3.1 Thread&#xff0c;ThreadLocal&#xff0c;ThreadLocalMap 关系3.2 总结4.ThreadLocal内存泄露问题4.1 什么是内存泄漏…

PCIE 学习笔记(入门简介)

PCIE 学习笔记书到用时方恨少啊&#xff0c;一年前学PCIE的笔记&#xff0c;再拿出来瞅瞅。发到博客上&#xff0c;方便看。PCIE基础PCIE和PCI的不同PCIE采用差分信号传输&#xff0c;并且是dual-simplex传输——每条lane上有TX通道和RX通道&#xff0c;所以每条lane上的信号是…

DBeaver连接达梦数据库

1、下载Dbeaver安装包 1、官网下载&#xff1a;Download | DBeaver Community 2、下载完成后双击运行.exe文件&#xff0c;进行安装 2、配置达梦数据库驱动 1、达梦数据库驱动下载&#xff1a;Mybatis 框架 | 达梦技术文档 2、为DBeaver添加驱动 3、自定义DM驱动管理器的相关配…

购买低代码平台,要考量哪些指标?

近些年来&#xff0c;低代码平台的热度在逐渐上升&#xff0c;可以看出企业数字化转型得速度也在逐渐加快。企业的数字开发需求越来越强&#xff0c;市场之间的竞争也愈演愈烈。特别是对于中小型企业&#xff0c;既要考虑到产品功能需求&#xff0c;又要考虑成本压力&#xff0…

安卓小游戏:飞机大战

安卓小游戏&#xff1a;飞机大战 前言 前面写了十二篇自定义view的博客&#xff0c;说实话写的还是有点无聊了&#xff0c;最近调整了一下&#xff0c;觉得还是要对开发有热情&#xff0c;就写了点小游戏&#xff0c;现在抽时间把博客也写一写&#xff0c;希望读者喜欢。 需…

渲染速度特别慢,使用云渲染会快多少?

设计师在使用软件制作效果图和动画师在制作动画时&#xff0c;其中有一个比较关键的环节就是渲染成像&#xff0c;渲染的效率主要跟使用的电脑显卡或CPU性能有关&#xff0c;如果性能太低&#xff0c;渲染的速度会很慢&#xff0c;拉长了项目整体的交付周期&#xff0c;云渲染速…

反转链表的两种方法

大家好&#xff0c;今天和大家分享的是反转链表的两种方法&#xff0c;第一种是用泛型编程里面的STL&#xff0c;第二种是利用多个指针进行操作&#xff0c;小孩子才做选择&#xff0c;建议两个都学。我们往下看&#xff1a;一.使用vector容器ps&#xff1a;该方法对内存的需求…

LeetCode刷题--- 430. 扁平化多级双向链表(双指针)

文章目录一、编程题&#xff1a;430. 扁平化多级双向链表&#xff08;双指针&#xff09;1.题目描述2.示例1&#xff1a;3.示例2&#xff1a;4.示例3&#xff1a;5.提示&#xff1a;二、解题思路1.思路2.复杂度分析&#xff1a;3.算法图解三、代码实现总结一、编程题&#xff1…

网页防篡改实验(6)

实验简介 实验所属系列&#xff1a;网络攻防工具 实验对象&#xff1a; 本科/专科信息安全专业 相关课程及专业&#xff1a;信息网络安全概论、计算机网络 实验时数&#xff08;学分&#xff09;&#xff1a;2学时 实验类别&#xff1a;实践实验类 实验目的 1、了解网页防篡改…

7.数据库设计

学习过程参考&#xff08;后续章节同&#xff09; 【公开课】数据库系统概论&#xff08;王珊老师&#xff09;&#xff08;完结&#xff09; 《数据库系统概论》思维导图 第7章 数据库设计 | 数据库知识点整理 梳理 名词解释 数据库设计(database design)&#xff1a;数据库…

从2023年31省级政府工作报告看数据安全赛道 | 附下载

数字经济是支撑我国经济增长的新动能。据中国信息通信研究院数据&#xff0c;2021年我国数字经济规模超45万亿元、在GDP已占比40%&#xff0c;到2025年我国数字经济规模预计超60万亿元。春节前夕&#xff0c;地方两会陆续召开&#xff0c;从各地发布的2022年经济社会发展成绩来…

NodeJS与npm版本不一致时降级npm的方法

首先查看 Node.js 与 npm 版本对应关系&#xff1a;Node.js与npm版本查看。 安装 cnpm&#xff1a; npm install -g cnpm 查看一下 npm 和 cnpm 的镜像&#xff1a; npm config get registry cnpm config get registry 2 如果不是 https://registry.npm.taobao.org/ 的话就修…

【C++】CC++内存管理

就是你被爱情困住了&#xff1f;Wake up bro&#xff01; 文章目录一、C/C内存分布二、C语言中动态内存管理方式三、C中内存管理方式1.new和delete操作内置类型2.new和delete操作自定义类型&#xff08;仅限vs的底层实现机制&#xff0c;new和delete一定要匹配使用&#xff0c;…

【Linux】TCP网络编程流程

TCP网络编程流程 上一节博文我们提到了网络编程的基本流程 现在我们来了解TCP网络编程的流程 在这之前我们先要了解TCP 首先TCP是一种传输控制协议 在因特网协议族&#xff08;Internet protocol suite&#xff09;中&#xff0c;TCP层是位于IP层之上&#xff0c;应用层之…

MIT 6.S965 韩松课程 02

Lecture 02: Basics of Neural Networks TitleBasics of Neural NetworksLecturerSong HanDate09/13/2022Note AuthorGuangxuan Xiao (xgx)DescriptionReview the basics of deep learning and introduce efficiency metrics for neural networks. 回顾深度学习的基础知识&…

SparkSQL 核心编程

文章目录SparkSQL 核心编程1、新的起点2、SQL 语法1) 读取 json 文件创建 DataFrame2) 对 DataFrame 创建一个临时表3) 通过SQL语句实现查询全表3、DSL 语法1) 创建一个DataFrame2) 查看DataFrame的Schema信息3) 只查看"username"列数据4) 查看"username"列…

Elasticsearch(九)搜索---搜索辅助功能(下)--搜索性能分析

一、前言 上篇文章我们学习了ES的搜索辅助功能的一部分–分别是指定搜索返回的字段&#xff0c;搜索结果计数&#xff0c;分页&#xff0c;那么本次我们来学习一下ES的性能分析相关功能。 二、ES性能分析 在使用ES的过程中&#xff0c;有的搜索请求的响应比较慢&#xff0c;…

ChatGPT的火爆出圈,你对它有几分了解?

文章目录1.ChatGPT是什么&#xff1f;2.ChatGPT能做什么&#xff1f;2-1.什么是自然语言模型&#xff1f;3.ChatGPT带来的评价4.了解完ChatGPT之后&#xff0c;你会有什么反思&#xff1f;4-1.为什么微软不自己研发ChatGPT&#xff1f;4-2.Elon Musk为什么退出OpenAI公司&#…