异步编程
随着计算机的不断发展,用户对计算机应用的要求越来越高,需要提供更多、更只能、响应速度更快的功能。这就离不开异步编程的话题。同时,随着互联网时代的崛起,网络应用要求能够支持更多的并发量,这显然也要用到大量的异步编程。
- 什么是异步
有异步就不得步提另一个概念:同步,这样的理解是错误的,咱们不能以字面的意思去理解它。同步,英文名叫做 Syncjrpmozation 。它是指同一时间只能做一件事情,也就是说一件事情做完了才能做另外一件事情。
异步的实现
多线程:
线程可以理解成一个应用程序中的执行任务,每一个程序至少会有一个线程,它被成为主线程。如果想实现异步处理,就可以通过开始多个线程,这些线程可以同时执行。只是异步实现的一种方式。
回调函数实现异步
JavaScript 引擎是以单线程的机制来运行代码的。所以在 JavaScript中想要实现异步就只有采用单线程非阻塞式的方式。早期的时候,单线程非阻塞通过回调函数来实现,例如:
console.log("start");
setTimeout(function(){
console.log("timeout");
},5000);
console.log("end");
这段代码的最终执行结果是:
start
end
// 等待五秒之后
timeout
从结果可以看出end的输出并没有等待时间函数执行完,实际上setTimeout
就是异步的实现。
代码的执行顺序如下:
首先执行输出字符串"start",然后开始执行setTimeout
函数。由于它是一个异步操作,所以它会被分为两部分来执行,先调用setTimeout
方法,然后把要执行的函数放到一个队列中。代码继续往下执行,当所有的代码执行完后,放到队列中的函数才会被执行。
这样一来,所有异步执行的函数都不会被阻塞其他代码的执行。虽然这些代码都不是同时执行,但是由于任何代码都不会被阻塞,所以执行效率很快。如下图:
回调函数实现异步的缺陷
很长一段时间,JavaScript中实现异步都是采用回调函数的形式,但是这种形式有一个最大的缺陷,就是容易产生回调低于。
举个例子,如果我们希望在异步操作中加入同步的行为。比如,我想打印五句话,但是每一句话都在前一句话的基础上延迟两秒输出。如:
setTimeout(function () {
console.log("1");
setTimeout(function () {
console.log("2");
setTimeout(function () {
console.log("3");
setTimeout(function () {
console.log("4");
setTimeout(function () {
console.log("5");
});
});
});
});
});
这段代码能够实现功能,到那时总觉得哪里不对。如果输出的内容越来越多,嵌套的代码也会增多。造成这种情况的罪魁祸首的就是回调函数。
因为:如果要前面的异步操作完成之后再进行接下来的操作,那只能在它的回调函数;中进行,这样就会越套越多,代码越来越复杂,这种情况被称之为:"回调地狱"
Promise 实现异步
ES6规定:Promise 对象是一个构造函数,通过new
调用来生成一个Promise实例。
- 解决js回调地狱
new Promise
整个返回的是一个promise
,promise
里面就有一个then
方法和一个catch
方法- 在promise里面执行异步的操作
- 如果异步操作成功,调用resolve
- 如果异步操作失败,调用reject
const outTime = function (time) {
return new Promise(function (resolve, reject) {
//处理异步代码
setTimeout(function () {
resolve();
},time)
})
}
outTime(2000).then(function(){
console.log("Hello")
return outTime(2000);
}).then(function(){
console.log("Hello")
return outTime(2000);
}).then(function(){
console.log("Hello")
return outTime(2000);
}).then(function(){
console.log("Hello")
return outTime(2000);
}).then(function(){
console.log("Hello")
})
###ES7 实现异步的方法
async、await 这个称之为异步的终极解决方案,因为这种方式来实现的异步,让异步代码看上去就像同步代码一样。
- async
async
是修饰函数的一个关键字,表示一个函数是一个异步的函数。
const Timer= function () {
return new Promise(function (resolve, reject) {
//处理异步代码
setTimeout(function () {
resolve("Hello World");
},2000)
})
}
async function test(){
console.log(await Timer())
}
test()