发布于 4年前

promise和generator

js里的回调地狱是个极其蛋疼的事,promise可以比较好的解决方法,但他也有缺点,这里先谈他的基本用法。
如果我们不用promise写异步操作的时候,假设我们请求3个文件:

1.txt;
2.txt;
3.txt

在js里我们会这么写:

$.ajax({
                url('./upload/1.txt'),
                success(data) {
                    //do something
                    $.ajax({
                        url('./upload/2.txt'),
                        success(data) {
                            //do something
                            $.ajax({
                                url('./upload/3.txt'),
                                success(data) {
                                    //do something

                                },
                                error(err) {
                                    alert('出错了')
                                }
                            })
                        },
                        error(err) {
                            alert('出错了')
                        }
                    })
                },
                error(err) {
                    alert('出错了')
                }
            })

这也太恐怖了吧
promise解决的其实就是用同步的写法来写异步操作
promise里面有个all方法,里面放我们要执行的异步操作,在所有操作完成后调用then方法,这个方法有两个参数resolve和reject,操作成功和操作失败。来看例子:

    Promise.all([
        $({url:'./upload/1.txt'}),
        $({url:'./upload/2.txt'}),
        $({url:'./upload/3.txt'})
    ]).then(resolve=>{
    //do something
    },reject=>{
        alert('出错了')
    })

所有的异步操作成功会才会调用resolve,否则就调用reject。这个写法就舒服多了。
generator函数简单的来说就是可以暂停目前在执行的函数,去执行其他的代码,什么时候你想继续执行了继续来调用就可以继续来执行了。
创建一个generator函数:

function *show(){
    //this is a generator function
}

没错,就是在函数名称前加了个*号,这里面有一个yeild值得我们来说说。
在创建完generator函数之后,我们需要来执行他,和普通函数的执行不同,generator函数是这样执行的:

function *show(){
 alert('do something');
 yeild;
 alert('continue');
}

let g1=show();
g1.next()//do something
alert('do other');//do other
g1.next()//continue

函数里面出现了一个yield,这个就是我们从开始执行到暂停的地方,调用g1.next()就执行到这里,然后程序就从第一个g1.next()处开始执行alert('do other');执行完之后我们在调用g1.next()就又回到show函数中从yeild处开始往下执行。
其中yeild还可以传参数:

function *show(){
 alert('do something');
 yeild 5;
}
let a=g1.next();//a=5

也可以传参数进去:

function *show(){
 alert('do something');
 let a=yeild;
 alert(a)//6
}
g1.next();//do something
g1.next(6)
©2020 edoou.com   京ICP备16001874号-3