15.回调函数

109 阅读3分钟

回调函数不是新语法,就是把函数作为另一个函数的参数,传递到另一个函数outer中,在outer中以形参的方式调用这个函数,那这个函数就是outer的回调函数

       function outer(fn){
           fn()
           console.log('回到家给我发个消息)
       }
       function inner(){
           console.log('我到家了)
       }
       outer(inner)

回调地狱

就是回调函数的嵌套使用.
        function help (success, error) {
        let time = Math.floor(Math.random() * 3000 + 2000)
        setTimeout(function () {
            console.log(time);
            // 这个时候我们要根据用时的不同做出不同的处理
            if (time > 3500) {
                console.log('你怎么那么慢');
                error()
            } else {
                console.log('既然你这么快');
                success()
            }
        },time)
    }
    help(function success(){
        console.log('那你就再帮我买个面包')
        help(function success(){
            console.log('你再帮我买瓶水吧')
            help(function success(){
                console.log('我还想要一包湿纸巾')
                    help(function success(){
                        console.log('对了,我还需要一个漂亮的盘子')
                    },function error(){
                        console.log('那么慢,你是不是嫌我让你买的东西多不想买啊')
                    })
            },error(){
                console.log('买瓶水那么慢我都要渴死了')
            })
        },function error(){
            console.log('额,你怎么买个面包那么慢')
        })
    },function error(){
        console.log('我自己去买吧!!!')
    })
    很显然,这段代码的可读性差,是不利于后期维护的,因为我们需要想出一个办法解决这个问题.
    

Promise

ES6中新增了内置构造函数Promise,它的出现就是为了解决回调地狱的.
语法:const 变量名 = new Promise(function(参数){这里书写你想做的事情})
Promise的状态
    => pending: 是一种持续的状态
    => fulfilled: 是一种成功的状态
    => rejected: 是一种失败的状态
Promise的状态转换
    => Promise 中的状态转换只转换一次
    => 要不就是从:  pending => fulfilled
    => 要不就是从:  pending => rejected
**如何执行?**
    => 也就是在我们的 Promise 对象中有两个方法
    => 第一个: then() 
        -> 语法: Promise对象.then(function () {})
        -> 执行时机: 当我们的状态从 持续到成功的时候执行then里面的函数
        -> then()里面的函数就是我们成功的时候的回调函数
    => 第二个: catch()
        -> 语法: Promise对象.catch(function () {})
        -> 执行时机: 当我们的状态从 持续到失败的时候执行catch里面的函数
        -> catch()里面的函数就是我们失败的时候的回调函数
        
        
        let p = new Promise(function (resolve, reject) {
        // resolve: 是一个状态转换函数 , 从持续状态转变为 成功的时候执行
        // reject: 也是一个状态转换函数 , 从持续转变为失败的时候执行这个函数
        let time = Math.floor(Math.random() * 3000 + 2000)
        setTimeout(function () {
            console.log(time);
            if (time > 3500) {
                reject('我就要回去')
            } else {
                resolve('不客气')
            }
        },time)
        })
        // 使用
        p.then(function (res) {
            console.log('谢谢你',res);
        })
        p.catch(function (res) {
            console.log('你不要回来了',res);
        })

Promise的进阶语法

    help()
    .then(result => {
        console.log('谢谢你',result);
        // 这里我们返回一个新的 Promise 对象
        return help()
    })
    // 需求2: 当班长给我买完水以后 , 再给我买一包烟
    .then(() => {
        console.log('我买好了');
        return help()
    })
    // 需求3: 当班长给我买完烟以后 , 在给我买一个打火机
    .then(() => {
        console.log('都买完了');
    })

async 和 await

        function help () {
        // 需要出现(定义)一个Promise对象
        let p = new Promise(function (resolve, reject) {
            let time = Math.floor(Math.random() * 3000 )
            setTimeout(function () {
                console.log(time);
                if (time > 2000) {
                    reject('我就要回去')
                } else {
                    resolve('没关系')
                }
            },time)
        })
        // 这里需要返回一个 Promise 对象
        return p
        }
        
        async function fun() {
        // 需求1: 当班长买完自己的东西以后在给我买一瓶水
        let res = await help()

        console.log(res);
        // 需求2: 当班长给我买完水以后 , 再给我买一包烟
        let res1 = await help()

        // 需求3: 当班长给我买完烟以后 , 在给我买一个打火机
        let res2 = await help()
        }
        fun()