理解JavaScript中的promise [英] Understanding of promises in JavaScript

查看:79
本文介绍了理解JavaScript中的promise的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我对JavaScript进行了相当多的编码,虽然我认为我确实理解了承诺的运作,但我不确定我是否完全理解承诺给JS世界带来的好处。考虑下面的代码,只是使用包含更多调用的回调的异步调用等等。

I code JavaScript quite a bit and although I think I do understand workings of promises I'm not sure if I fully understand advantages that promises bring to JS world. Consider code below, simply asynchronous calls with callbacks containing furhter calls and so on.

(function doWorkOldSchool() {

    setTimeout(function() {

        // once done resolve promise

        console.log("work done");

        setTimeout(function goHome() {

            // once done resolve promise

            console.log("got home");

            try {

                setTimeout(function cookDinner() {

                    // this exception will not be caught

                    throw "No ingredients for dinner!";
                    console.log("dinner cooked");

                    setTimeout(function goToSleep() {

                        // once done resolve promise

                        console.log("go to sleep");

                    }, 2000);

                }, 2000);

            } catch (ex) {
                console.log(ex);
            }

        }, 2000);

    }, 2000);

}());

我看到一个问题:


  1. 在回调中抛出异常是没用的。是否正确的说,当抛出调用发生时,这些抛出调用超出范围,因此异常无法调用并且一直冒泡到顶部?如何处理这种异常?

  1. Exceptions thrown inside of callbacks are useless. Is it correct to say that as throw calls happen these throw calls are out of scope hence the exception cannot be called and bubbles all the way to the top? How this sort of exception can be dealt with?

第二个问题我看到这个嵌套业务可能会变得很深,即使你可以保持回调函数代码在外面setTimeout代码,它可能会变得一团糟。

Second problem I see that this nesting business might get really deep and even though you can keep callback functions code outside of the setTimeout code, it might become a mess.

所以首先有人可以澄清是否还有其他任何东西这种编码有明显的问题或优势吗?

So first could someone please clarify if there is anything else that is obvious problem or advantage of this sort of coding?

现在,我准备的程序真的做了同样的事情,但这次使用了承诺:

Now, below I prepared program that does the same thing really, but this time using promises:

function doWork() {

    return new Promise(function(res, rej) {

        // do your asynchronous stuff

        setTimeout(function() {

            // once done resolve promise

            res("work done");

        }, 2000);

    });
}


function goHome(succ) {

    console.log(succ);

    return new Promise(function(res, rej) {

        // do your asynchronous stuff

        setTimeout(function() {

            // once done resolve promise

            res("got home");

        }, 2000);

    });
}


function cookDinner(succ) {

    console.log(succ);

    //if exception thrown here it will be caught by chained err handler
    throw "No ingredients for dinner Exception!";

    return new Promise(function(res, rej) {

        // do your asynchronous stuff

        setTimeout(function() {

            // something went wrong so instead of using throw we reject the promise

            rej("No ingredients for dinner!");

            // once done resolve promise

        }, 2000);

    });
}


function goToSleep(succ) {

    console.log(succ);

    return new Promise(function(res, rej) {

        // do your asynchronous stuff

        setTimeout(function() {

            // once done resolve promise

            res("zzz... zz..");

        }, 2000);

    });
}


doWork()
    .then(goHome)
    .then(cookDinner)
    .then(goToSleep)
    .then(function(succ) {

        console.log(succ);

    }, function(err) {
        console.log(err);
    });

与之前的解决方案相比,我认为这种方法没有明显的问题,除了你显然必须了解承诺编码/维护这件事。然而,优点是:

Comparing to previous solution I see no obvious problems with this approach, apart from you obviously must have understanding of promises to code/maintain this thing. Advantages would be however:


  1. 抛出的异常INSIDE OF处理程序将被捕获在更进一步链接的错误处理程序中。

  1. the exception thrown INSIDE OF handlers will be caught in err handler that is chained somewhere further.

被拒绝的Promise将被链式错误处理程序捕获

the rejected Promises will be caught by chained err handler

代码更清晰

现在,我的理解是正确的还是每种方法还有其他优点/缺点?

Now, is my understanding correct or are there any other advantages/disadvantages of each approach?

推荐答案

你的代码采用了一些反模式,你永远不应该创建承诺(例如通过新的承诺 ,延迟等等在应用程序代码中。你也必须永远不要将回调与promises混合,因为这样你就会失去异常冒泡(承诺点)并使你的代码变得非常冗长。

Your code is employing some anti patterns, you should never create promises (e.g. by new Promise, "deferreds" and so on) in application code. You must also never mix callbacks with promises because then you lose exception bubbling (the point of promises) and make your code super verbose.

你可以使用一个库或实现一个推迟自己:

You can use a library or implement a delay yourself:

function delay(ms, val) {
     return new Promise(function(res){setTimeout(res.bind(null, val), ms);});
}

然后:

function doWork() {
    return delay(2000, "work done");
}

doWork()
    .then(function(succ) {
        console.log(succ);
        return delay(2000, "got home");
    })
    .then(function(succ) {
        console.log(succ);
        // Never throw strings, yet another anti-pattern
        throw new Error("No ingredients for dinner Exception!");
        // Pointless to add code after throw
    })
    .then(function(succ) {
        return delay(2000, "zzz.. zz..");
    })
    // Don't use the second argument of .then, use .catch
    .catch(function(err) {
        console.log("error: ", err);
    });

为什么要使用 .catch 代替第二个论点?那么,与你同步编写它的方式相比:

Why should you use .catch instead of the second argument? Well, compare to how you would write it synchronously:

try {
    doWork();
    console.log("work done");
    sleep(2000);
    console.log("got home");
    sleep(2000);
    throw new Error("No ingredients for dinner Exception!";)
    sleep(2000);
    console.log("zzz.. zz..");
}
catch(e) {
    console.log("error: ", err);
}

获取它?

这篇关于理解JavaScript中的promise的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆