石川es6课程---12、Promise
一、总结
一句话总结:
用同步的方式来书写异步代码,让异步书写变的特别简单
用同步的方式来书写异步代码
Promise 让异步操作写起来,像在写同步操作的流程,不必一层层地嵌套回调函数
改善了可读性,对于多层嵌套的回调函数很方便
充当异步操作与回调函数之间的中介,使得异步操作具备同步操作的接口
1、传统的异步写法?
嵌套操作
ajax('./banners',function(banner_data){ ajax('./hotItems',function(hotItem_data){ ajax('./slides',function(slide_data){ },function(){alert("读取失败")}) },function(){alert("读取失败")}) },function(){alert("读取失败")})
2、传统的同步操作数据?
同时只能做一件事
let banner_data=ajax_sync('./banners') let hotItem_data=ajax_sync('./hotItems') let slide_data=ajax_sync('./slides')传统的同步操作数据
3、jquery中ajax方法的回调函数的作用是什么?
$.ajax是不同操作的回调函数,$.post是发送成功的回调函数
如果要处理$.ajax()得到的数据,则需要使用回调函数。beforeSend、error、dataFilter、success、complete。 beforeSend 在发送请求之前调用,并且传入一个XMLHttpRequest作为参数。 error 在请求出错时调用。传入XMLHttpRequest对象,描述错误类型的字符串以及一个异常对象(如果有的话) dataFilter 在请求成功之后调用。传入返回的数据以及"dataType"参数的值。并且必须返回新的数据(可能是处理过的)传递给success回调函数。 success 当请求之后调用。传入返回后的数据,以及包含成功代码的字符串。 complete 当请求完成之后调用这个函数,无论成功或失败。传入XMLHttpRequest对象,以及一个包含成功或错误代码的字符串。 $.ajax({ url: "test.html", cache: false, success: function(html){ $("#results").append(html); } });
4、Promise实例?
用Promise.all(),全部成功一个回调函数,失败一个回调函数
Promise.all()函数 let p1=new Promise(function(resolve,reject){ //异步代码 //resolve成功 //reject失败 $.ajax({ url:'https://easy-mock.com/mock/5cadb508b56fc13f6206ad0e/example/arr.txt', type:'get', dataType:'json', success(arr){ resolve(arr) }, error(err){ reject(err) } }) }) let p2=new Promise(function(resolve,reject){ $.ajax({ url:'https://easy-mock.com/mock/5cadb508b56fc13f6206ad0e/example/json.txt', dataType:'json', type:'get', success:function(data){ resolve(data) }, error:function(err){ reject(err) } }) }) Promise.all([p1,p2]).then(function(arr){ let [res1,res2]=arr console.log(res1,res2) },function(){ alert("至少一个失败") })
二、Promise
-
异步和同步
- 异步,操作之间没有关系,同时执行多个操作, 代码复杂
- 同步,同时只能做一件事,代码简单
-
Promise 对象
- 用同步的方式来书写异步代码
- Promise 让异步操作写起来,像在写同步操作的流程,不必一层层地嵌套回调函数
- 改善了可读性,对于多层嵌套的回调函数很方便
- 充当异步操作与回调函数之间的中介,使得异步操作具备同步操作的接口
-
Promise 也是一个构造函数
- 接受一个回调函数f1作为参数,f1里面是异步操作的代码
- 返回的p1就是一个 Promise 实例
- 所有异步任务都返回一个 Promise 实例
- Promise 实例有一个then方法,用来指定下一步的回调函数
function f1(resolve, reject) {
// 异步代码...
}
var p1 = new Promise(f1);
p1.then(f2); // f1的异步操作执行完成,就会执行f2。
- Promise 使得异步流程可以写成同步流程
// 传统写法
step1(function (value1) {
step2(value1, function(value2) {
step3(value2, function(value3) {
step4(value3, function(value4) {
// ...
});
});
});
});
// Promise 的写法
(new Promise(step1))
.then(step2)
.then(step3)
.then(step4);
- Promise.all(promiseArray)方法
- 将多个Promise对象实例包装,生成并返回一个新的Promise实例
- promise数组中所有的promise实例都变为resolve的时候,该方法才会返回
- 并将所有结果传递results数组中
- promise数组中任何一个promise为reject的话,则整个Promise.all调用会立即终止,并返回一个reject的新的promise对象
var p1 = Promise.resolve(1),
p2 = Promise.resolve(2),
p3 = Promise.resolve(3);
Promise.all([p1, p2, p3]).then(function (results) {
console.log(results); // [1, 2, 3]
});
- Promise.race([p1, p2, p3])
- Promse.race就是赛跑的意思
- 哪个结果获得的快,就返回那个结果
- 不管结果本身是成功状态还是失败状态
3、Promise
- 异步请求/操作
- 异步:操作之间没有任何关系,可以同时进行多个操作
- 同步:同时只能做一件事
- 优缺点
- 异步缺点:代码更复杂
- 同步优点:代码简单
//异步操作读取数据
ajax('./banners',function(banner_data){
ajax('./hotItems',function(hotItem_data){
ajax('./slides',function(slide_data){
},function(){alert("读取失败")})
},function(){alert("读取失败")})
},function(){alert("读取失败")})
//同步操作数据
let banner_data=ajax_sync('./banners')
let hotItem_data=ajax_sync('./hotItems')
let slide_data=ajax_sync('./slides')
- Promise——清除异步操作
- 本质:用同步一样的方式写异步
- 用法: 基本的封装ajax
let p1=new Promise(function(resolve,reject){
//异步代码
//resolve成功
//reject失败
$.ajax({
url:'https://easy-mock.com/mock/5cadb508b56fc13f6206ad0e/example/arr.txt',
type:'get',
dataType:'json',
success(arr){
resolve(arr)
},
error(err){
reject(err)
}
})
})
p1.then(function(){},function(){})
Promise.all()函数
let p1=new Promise(function(resolve,reject){
//异步代码
//resolve成功
//reject失败
$.ajax({
url:'https://easy-mock.com/mock/5cadb508b56fc13f6206ad0e/example/arr.txt',
type:'get',
dataType:'json',
success(arr){
resolve(arr)
},
error(err){
reject(err)
}
})
})
let p2=new Promise(function(resolve,reject){
$.ajax({
url:'https://easy-mock.com/mock/5cadb508b56fc13f6206ad0e/example/json.txt',
dataType:'json',
type:'get',
success:function(data){
resolve(data)
},
error:function(err){
reject(err)
}
})
})
Promise.all([p1,p2]).then(function(arr){
let [res1,res2]=arr
console.log(res1,res2)
},function(){
alert("至少一个失败")
})
通用封装
function createPromise(url){
return new Promise(function(resolve,reject){
//异步代码
//resolve成功
//reject失败
$.ajax({
url:url,
type:'get',
dataType:'json',
success(arr){
resolve(arr)
},
error(err){
reject(err)
}
})
})
}
Promise.all([createPromise("https://easy-mock.com/mock/5cadb508b56fc13f6206ad0e/example/arr.txt"),createPromise("https://easy-mock.com/mock/5cadb508b56fc13f6206ad0e/example/json.txt")]).then(function(arr){
let [res1,res2]=arr
console.log(res1,res2)
},function(){
alert("至少一个失败")
})
- 有了promise之后的异步
Promise.all([$.ajax({]}),$.ajax({})]).then(
results=>{
//全部成功之后的操作
},err=>{
//失败
}
)
- Promise其他用法
- Promise.race() 竞速,与all区别是:只要有一个文件请求成功了就用谁,就会返回resolve