定义:指一块被分配的内存既不能使用,又不能回收,直到浏览器进程结束。
JavaScript在创建对象时会为它们分配内存,不再使用时会自动释放内存,这个过程称为垃圾收集。
四种常见的内存泄漏:
捕获 > 目标 > 冒泡
在捕获阶段,事件通过父元素向下传递到目标元素
然后到达目标元素,冒泡开始
在JavaScript中,每个函数都有自己的作用域。
作用域基本上是变量以及如何通过名称访问这些变量的规则的集合。
只有函数汇总的代码才能访问函数作用域内的变量。
在同一个作用域中的变量名必须是唯一的。一个作用域可以嵌套在另一个作用域内。如果一个作用域嵌套在另一个作用域内,最内部作用域的代码可以访问另一个作用域的变量。
null == undefined // true
null === undefined // false
typeof(null) // object
typeof(undefined) // undefined
防抖
触发高频事件后n秒内函数只会执行一次,如果n秒内高频事件再次被触发,则重新计算事件。
应用场景:
思路:每次触发事件时都取消之前的延时调用方法
节流
高频事件触发,但在n秒内只会执行一次,所以节流会稀释函数的执行频率。
使用场景:
思路:每次触发事件时都判断当前是否有等待执行的延时函数
原型:
原型链:
特点:
8种数据类型:
Ajax 的核心是 JavaScript对象 XMLHttpRequest。该对象在 Internet Explorer5中首次引入,是一种支持异步请求的技术。通过XMLHttpRequest对选哪个,开发人员可以在页面加载以后进行页面的局部更新。
1.callback
指通过函数传参传递到其他执行代码的,某一块可执行代码的引用,被主函数调用后又回到主函数
缺点:如果存在多个任务,需要层层嵌套,形成回调地狱,代码会显得冗余且耦合度很高。降低代码的阅读性和可维护性
2.promise
Promise是一个对象,可以获取异步操作的消息。
Promise对象有两个特点:
常用于解决异步回调问题,可以将回调函数的嵌套改为链式调用。
优点:解决回调地狱
缺点:还是有些多余的代码,如被Promise包装的函数有一堆的new Promise、then、catch
3.generator函数
是ES6提供的一种异步解决方案,由每执行一次函数返回的是一个遍历器对象,返回的对象可以依次遍历Generator里面的每一个状态
需要用遍历器对象的next方法来执行函数
Generator有三个特征:
优点:相比Promise在写法上更加精简且逻辑清晰
4.async
是Generator函数的语法糖
相比Generator函数,async函数在写法上的区别就是async替代了*,await替代了yield,并且async自带执行器
async函数返回的Promise,必须等到函数体内所有await后面的Promise对象都执行完毕后,或者return或者抛错之后才能改变状态;也就是只有async里面的异步操作全部操作完,才能回到主任务来,并且在then方法里面继续执行主任务。
async与Promise、Generator函数之间的对比
// callback异步
function callback() {
let readFile;
readFile(fileA, function (data) {
readFile(fileB, function (data) {
// ......
});
});
}
// promise
function getData() {
let require = new Promise((res, rej) => {
res(), rej();
});
require
.then((res) => {
let result = res.data;
})
.catch((err) => {
let error = err.message;
});
}
// generator
function * foo(){
yield getFirstData;
yield getSecondData;
return getThirdData
}
let require = foo()
require.next()
require.next()
// async
let getListData = async function(){
let result = await reqGetListData()
if(result.code = 200){
// ...
}
}
闭包: 子函数调用父函数上的变量,返回给外界去使用,那么称子函数就是一个闭包
优点:缓存数据
缺点:内存泄漏,溢出
闭包作用:自执行函数,不会污染全局变量,形成块儿级作用域 变量私有化