qt5示例源程序执行不出

    科技2026-08-22  7

    qt5示例源程序执行不出

    Confused about the order in which JavaScript promises execute? I was too. Working through some examples and referencing the JavaScript spec helped better my understanding — hopefully it can do the same for you.

    是否对JavaScript承诺的执行顺序感到困惑? 我也是。 通过一些示例并参考JavaScript规范可以帮助我更好地理解-希望它可以为您做同样的事情。

    承诺国 (Promise States)

    Before we dive into the examples, let’s review some helpful background knowledge.

    在深入研究示例之前,让我们回顾一些有用的背景知识。

    A promise can be in one of three mutually exclusive states: fulfilled, rejected, or pending. Here is how spec 26.6 defines these states.

    一个承诺可以处于以下三种互斥状态之一:已实现 , 被拒绝或未决 。 规范26.6定义了这些状态。

    A promise p is fulfilled if p.then(f, r) will immediately enqueue a Job to call the function f.

    如果p.then(f, r)将立即让Job进入调用函数f p.then(f, r)则诺言p得到满足 。

    A promise p is rejected if p.then(f, r) will immediately enqueue a Job to call the function r.

    如果p.then(f, r)立即使Job入队以调用函数r p.then(f, r)则承诺p被拒绝 。

    A promise is pending if it is neither fulfilled nor rejected.

    如果诺言既未实现也未拒绝,则它是未决的 。

    There are two more terms to be aware of: settled and resolved.

    还有两个术语需要注意: 解决和解决 。

    A promise is said to be settled if it is not pending, i.e. if it is either fulfilled or rejected.

    允诺说,如果它不挂起,如果它要么履行或拒绝进行结算 ,即。

    A promise is resolved if it is settled or if it has been “locked in” to match the state of another promise. Attempting to resolve or reject a resolved promise has no effect. A promise is unresolved if it is not resolved. An unresolved promise is always in the pending state. A resolved promise may be pending, fulfilled or rejected.

    如果一个承诺已结算或已被“锁定”以匹配另一个承诺的状态,则该承诺将得到解决 。 尝试解决或拒绝已解决的承诺没有任何效果。 如果未解决承诺,则无法解决 。 未解决的承诺始终处于待处理状态。 已解决的承诺可能待定 ,已实现或被拒绝 。

    规则 (Rules)

    We’ll go over things in more detail below, but here are some high-level rules that should be helpful when trying to understand promises. I recommend reading through the examples while referring to these rules, as opposed to trying to understand these rules thoroughly before going through the examples.

    我们将在下面更详细地介绍这些内容,但是这里有一些高级规则在尝试理解承诺时会有所帮助。 我建议在参考这些规则时通读示例,而不是在遍历示例之前尝试全面了解这些规则。

    A promise’s executor function runs synchronously.

    许诺的执行程序功能同步运行。

    Calling Promise.prototype.then() on a fulfilled promise adds a job to the job queue (see spec 8.4, spec 26.6).

    在已实现的promise上调用Promise.prototype.then()会将作业添加到作业队列中(请参见规范8.4 , 规范26.6 )。

    Promise.prototype.then() returns a pending promise. The promise gets fulfilled (or rejected) when the job it enqueued runs (see spec 26.6.5.4)

    Promise.prototype.then()返回待处理的Promise.prototype.then() 。 在排队的作业运行时,promise将兑现(或拒绝)(请参见规范26.6.5.4 )

    Jobs are run in the order they are enqueued.

    作业按入队顺序运行。

    Jobs are only run when “there is no running execution context and the execution context stack is empty,” e.g. once all the synchronous code in a script has finished (see spec 8.4).

    仅当“没有正在运行的执行上下文并且执行上下文堆栈为空”时才运行作业,例如,脚本中的所有同步代码都完成后(请参见规范8.4 )。

    You can think of await in terms of Promise.prototype.then() (see Example #5 and Example #6, see this StackOverflow post).

    您可以根据Promise.prototype.then()来考虑await (请参见示例5和示例6,请参阅此StackOverflow帖子 )。

    获取代码 (Get the Code)

    You can find all these examples on GitHub here.

    你可以找到所有这些例子在GitHub上这里 。

    Note that the examples make use of util.js, which you can find here.

    请注意,这些示例使用了util.js ,您可以在此处找到。

    Example#1 —简单介绍 (Example #1 — A simple introduction)

    Code

    getFulfilledPromise("foo") .then(logThen.bind(null, "1")) .then(logThen.bind(null, "2"));console.log("After creating promise");

    Logs

    日志

    Promise executor, result will be fooAfter creating promise[1] Promise then, result = foo[2] Promise then, result = foo

    Explanation

    说明

    We can understand this using rules #1, #2, #4, and #5.

    我们可以使用规则#1,#2,#4和#5来理解这一点。

    Each call to .then() adds a job to the queue (if we want to be really specific, this is called the “microtask queue”, see here for more details). However, these jobs only run after the script finishes, which is why After creating promise gets logged before the last two lines.

    每次对.then()调用都会在队列中添加一个作业(如果我们真的很具体,则称为“微任务队列”,更多信息请参见此处 )。 但是,这些作业仅在脚本完成后才运行,这就是为什么After creating promise后在最后两行之前记录日志的原因。

    示例#2 —在已实现的诺言上调用.then() (Example #2 — Calling .then() on a fulfilled promise)

    Code

    import { addLoggingToPromiseThen, getFulfilledPromise, logThen,} from "../util.js";addLoggingToPromiseThen();const prom1 = getFulfilledPromise("prom1");const prom2 = getFulfilledPromise("prom2");prom2.then(logThen.bind(null, "1"));prom2.then(logThen.bind(null, "2"));prom1.then(logThen.bind(null, "3"));prom1.then(logThen.bind(null, "4"));

    Logs

    日志

    Promise executor, result will be prom1Promise executor, result will be prom2In Promise.prototype.then Promise { 'prom2' }In Promise.prototype.then Promise { 'prom2' }In Promise.prototype.then Promise { 'prom1' }In Promise.prototype.then Promise { 'prom1' }[1] Promise then, result = prom2[2] Promise then, result = prom2[3] Promise then, result = prom1[4] Promise then, result = prom1

    Explanation

    说明

    We can understand this using rules #1, #2, #4, and #5 (the same rules as the first example).

    我们可以使用规则#1,#2,#4和#5(与第一个示例相同的规则)来理解这一点。

    Both prom1 and prom2 are fulfilled. We know from spec 26.6 that calling p.then(f, r) on a fulfilled promise p will “immediately enqueue a Job to call the function f.” This means that the calls to logThen will be put into the job queue (see spec 8.4 for more info about the job queue) in the same order as they appear in the script. Finally, since jobs run in the same order as they were enqueued (see spec 8.4.4), the logs appear in sequential order.

    prom1和prom2都已实现。 从规范26.6可以知道p.then(f, r)在已实现的诺言p上调用p.then(f, r)将“立即让Job排队以调用函数f 。 这意味着对logThen的调用将以与脚本中出现的顺序相同的顺序放入作业队列中(有关作业队列的更多信息,请参见规范8.4 )。 最后,由于作业以与入队相同的顺序运行( 请参见规范8.4.4 ),因此日志按顺序出现。

    Example#3 —交错执行 (Example #3 — Interleaved execution)

    Code

    import { addLoggingToPromiseThen, getFulfilledPromise, logThen,} from "../util.js";addLoggingToPromiseThen();const prom1 = getFulfilledPromise("prom1");const prom2 = prom1.then(logThen.bind(null, "1"));const prom3 = prom2.then(logThen.bind(null, "2"));const prom4 = getFulfilledPromise("prom2");const prom5 = prom4.then(logThen.bind(null, "3"));const prom6 = prom5.then(logThen.bind(null, "4"));

    Logs

    日志

    Promise executor, result will be prom1In Promise.prototype.then Promise { 'prom1' }In Promise.prototype.then Promise { <pending> }Promise executor, result will be prom2In Promise.prototype.then Promise { 'prom2' }In Promise.prototype.then Promise { <pending> }[1] Promise then, result = prom1[3] Promise then, result = prom2[2] Promise then, result = prom1[4] Promise then, result = prom2

    Explanation

    说明

    We can understand this using rules #1, #2, #3, #4, and #5. This one will be a bit more tricky because of rule #3…

    我们可以使用规则#1,#2,#3,#4和#5来理解这一点。 由于第3条规则,这将变得有些棘手...

    First, note that getFulfilledPromise("prom1").then(...) does not return a fulfilled promise. We can confirm this by looking at the logs from Promise.prototype.then— only the initial call to then for each promise logs a fulfilled promise.

    首先,请注意getFulfilledPromise("prom1").then(...)不会返回已兑现的承诺。 我们可以通过查看从日志中证实了这一点Promise.prototype.then只有初始呼叫- then为每个承诺记录一个兑现承诺。

    So, let’s go through this line-by-line and see what happens.

    因此,让我们逐行浏览一下,看看会发生什么。

    const prom1 = getFulfilledPromise("prom1");. This just gets a fulfilled promise.

    const prom1 = getFulfilledPromise("prom1"); 。 这只是一个兑现的诺言。

    const prom2 = prom1.then(logThen.bind(null, "1"));. Here, .then() is called on a fulfilled promise, which means that the corresponding job gets immediately enqueued (we also saw this in the last example). The call returns a pending promise that will get fulfilled when the enqueued job runs. That is, the job will run our onFulfilled callback, which is logThen.bind(null, "1"), and it will fulfill prom2. Note that jobs will only start running after the script completes (spec 8.4)! See spec 26.6.5.4.1 to read more about the details. The main important part is this line:

    const prom2 = prom1.then(logThen.bind(null, "1")); 。 在这里, .then()是在已兑现的.then()上调用的,这意味着相应的作业将立即排队(我们在最后一个示例中也看到了)。 该调用返回一个待处理的诺言,当排队的作业运行时,该诺言将实现。 也就是说,作业将运行我们onFulfilled的回调,这是logThen.bind(null, "1")它将履行prom2 。 请注意,作业只会在脚本完成后开始运行( 规范8.4 )! 请参阅规格26.6.5.4.1,以了解有关详细信息的更多信息。 最重要的部分是以下行:

    const prom2 = prom1.then(logThen.bind(null, "1"));. Here, .then() is called on a fulfilled promise, which means that the corresponding job gets immediately enqueued (we also saw this in the last example). The call returns a pending promise that will get fulfilled when the enqueued job runs. That is, the job will run our onFulfilled callback, which is logThen.bind(null, "1"), and it will fulfill prom2. Note that jobs will only start running after the script completes (spec 8.4)! See spec 26.6.5.4.1 to read more about the details. The main important part is this line:“Perform HostEnqueuePromiseJob(fulfillJob.[[Job]], fulfillJob.[[Realm]]).”

    const prom2 = prom1.then(logThen.bind(null, "1")); 。 在这里, .then()是在已兑现的.then()上调用的,这意味着相应的作业将立即排队(我们在最后一个示例中也看到了)。 该调用返回一个待处理的诺言,当排队的作业运行时,该诺言将实现。 也就是说,作业将运行我们onFulfilled的回调,这是logThen.bind(null, "1")它将履行prom2 。 请注意,作业只会在脚本完成后开始运行( 规范8.4 )! 请参阅规格26.6.5.4.1,以了解有关详细信息的更多信息。 主要的重要部分是以下行: “执行 HostEnqueuePromiseJob (fulfillJob。[[Job]],fulfillJob。[[Realm]])。”

    At this point, here is the state of things.

    至此,这是事物的状态。

    "1" is shorthand for “the job that runs logThen.bind(null, "1").

    "1"是“运行logThen.bind(null, "1")的作业的简写。

    "1" is shorthand for “the job that runs logThen.bind(null, "1"). job_queue = ["1"]

    "1"是“运行logThen.bind(null, "1")的作业的简写。 job_queue = ["1"]

    const prom3 = prom2.then(logThen.bind(null, “2”));. Here, .then() is called on a pending promise. Spec 26.6.5.4.1 describes the behavior in this scenario. Here’s the relevant line:

    const prom3 = prom2.then(logThen.bind(null, “2”)); 。 在此, .then()在未完成的promise上被调用。 规范26.6.5.4.1描述了这种情况下的行为。 这是相关的行:

    const prom3 = prom2.then(logThen.bind(null, “2”));. Here, .then() is called on a pending promise. Spec 26.6.5.4.1 describes the behavior in this scenario. Here’s the relevant line:“Append fulfillReaction as the last element of the List that is promise.[[PromiseFulfillReactions]].”

    const prom3 = prom2.then(logThen.bind(null, “2”)); 。 在此, .then()在未完成的promise上被调用。 规范26.6.5.4.1描述了这种情况下的行为。 这是相关的行: “将promiseReaction追加 为诺言 的 List 的最后一个元素 。[[PromiseFulfillReactions]]。”

    In simple terms, this makes it so that when

    简单来说,这使得

    prom2 gets fulfilled, logThen.bind(null, "2")) will be called.

    prom2得到满足,将logThen.bind(null, "2")) 。

    prom2 gets fulfilled, logThen.bind(null, "2")) will be called.

    prom2得到满足,将logThen.bind(null, "2")) 。

    At this point, here is the state of things.

    至此,这是事物的状态。

    job_queue = ["1"]prom2_fulfill_reactions = ["2"]

    job_queue = ["1"]prom2_fulfill_reactions = ["2"]

    const prom4 = getFulfilledPromise("prom2");. This is basically the same as #1, it just gets a fulfilled promise.

    const prom4 = getFulfilledPromise("prom2"); 。 这基本上与#1相同,只是兑现了诺言。

    const prom5 = prom4.then(logThen.bind(null, "3"));. This is similar to #2. Since .then() is called on a fulfilled promise, the corresponding job gets immediately enqueued. Just as before, the job will run our callback and fulfill the promise returned by the call to .then() (which is prom5 in this case).

    const prom5 = prom4.then(logThen.bind(null, "3")); 。 这类似于#2。 由于.then()是在已实现的承诺上调用的,因此相应的作业将立即排队。 和以前一样,该作业将运行我们的回调并履行对prom5 .then()的调用所返回的承诺(在本例中为prom5 )。

    const prom5 = prom4.then(logThen.bind(null, "3"));. This is similar to #2. Since .then() is called on a fulfilled promise, the corresponding job gets immediately enqueued. Just as before, the job will run our callback and fulfill the promise returned by the call to .then() (which is prom5 in this case).

    const prom5 = prom4.then(logThen.bind(null, "3")); 。 这类似于#2。 由于.then()是在已实现的承诺上调用的,因此相应的作业将立即排队。 和以前一样,该作业将运行我们的回调并履行对prom5 .then()的调用所返回的承诺(在本例中为prom5 )。

    At this point, here is the state of things.

    至此,这是事物的状态。

    job_queue = ["1", "3"]prom2_fulfill_reactions = ["2"]

    job_queue = ["1", "3"]prom2_fulfill_reactions = ["2"]

    const prom6 = prom5.then(logThen.bind(null, "4"));. This is basically the same as #3. However, this time, we add a reaction to the list for prom5, not prom2.

    const prom6 = prom5.then(logThen.bind(null, "4")); 。 这基本上与#3相同。 但是,这次,我们将响应添加到prom5而不是prom2的列表中。

    const prom6 = prom5.then(logThen.bind(null, "4"));. This is basically the same as #3. However, this time, we add a reaction to the list for prom5, not prom2.

    const prom6 = prom5.then(logThen.bind(null, "4")); 。 这基本上与#3相同。 但是,这次,我们将响应添加到prom5而不是prom2的列表中。

    At this point, here is the state of things.

    至此,这是事物的状态。

    job_queue = ["1", "3"]prom2_fulfill_reactions = ["2"]prom5_fulfill_reactions = ["4"]

    job_queue = ["1", "3"]prom2_fulfill_reactions = ["2"]prom5_fulfill_reactions = ["4"]

    Alright, that’s it for the execution of the script itself. After the script runs, jobs from the job queue will start running. Here’s how that goes.

    好了,就是脚本本身的执行了。 脚本运行后,作业队列中的作业将开始运行。 这是怎么回事。

    Jobs get run in the order they were enqueued, so the job we’ve named "1" will execute first. This explains why [1] Promise then, result = prom1 is the first line that’s logged. Remember that this job not only runs our callback, but also fulfills prom2. If we take a look at spec 26.6.1.4 and spec 26.6.1.8, we can see that fulfilling a promise enqueues a job for each element in its “fulfill reactions” list. So, after this job runs, here is the state of things.

    作业按照入队的顺序运行,因此我们将首先执行名为"1"的作业。 这解释了为什么[1] Promise then, result = prom1是记录的第一行。 请记住,此作业不仅运行我们的回调,而且还实现了prom2 。 如果我们看一下规范26.6.1.4和规范26.6.1.8 ,我们可以看到,兑现承诺会为其“实现React”列表中的每个元素排队 。 因此,在此作业运行后,这里是状态。

    job_queue = ["3", "2"]prom5_fulfill_reactions = ["4"]

    job_queue = ["3", "2"]prom5_fulfill_reactions = ["4"]

    Job "1" gets run and popped from the queue and job "2" gets enqueued.

    作业"1"运行并从队列中弹出,并且作业"2"进入队列。

    The next job in the queue is "3", so that’s the next job that will execute. Just as with the first job, it will run the callback (thus logging [3] Promise then, result = prom2) and enqueue job "4". After this job runs, here is the state of things.

    队列中的下一个作业是"3" ,所以这是将要执行的下一个作业。 与第一个作业一样,它将运行回调(因此记录[3] Promise then, result = prom2 )并将作业"4"排队。 运行此作业后,这里是状态。

    job_queue = ["2", "4"]

    job_queue = ["2", "4"]

    It should be clear what happens at this point :).

    应该很清楚此时发生了什么:)。

    Example#4 —再次执行交错执行 (Example #4 — Interleaved execution, again)

    Code

    import { getFulfilledPromise, logThen } from "./util.js";const main = () => { new Promise((resolve, reject) => { console.log("Start main"); resolve(); }) .then(() => { console.log("Intermediate main"); }) .then(() => { console.log("End main"); });};getFulfilledPromise("outer") .then(logThen.bind(null, "1")) .then(logThen.bind(null, "2"));main();

    Logs

    日志

    Promise executor, result will be outerStart main[1] Promise then, result = outerIntermediate main[2] Promise then, result = outerEnd main

    Explanation

    说明

    We can use the same exact reasoning as Example #3 in order to understand this example. The differences are just syntactical:

    为了理解该示例,我们可以使用与示例3完全相同的推理。 区别只是语法上的:

    Instead of assigning all of the intermediate promises to variables, the .then() calls are chained inline.

    而不是将所有中间承诺分配给变量, .then()调用被内联链接。

    One of the promises is created in a function named main.

    承诺之一是在名为main的函数中创建的。

    Example#5 —交错执行,等待 (Example #5 — Interleaved execution, with await)

    Code

    const main = async () => { console.log("Start main"); await null; console.log("Intermediate main"); await null; console.log("End main");};getFulfilledPromise("outer") .then(logThen.bind(null, "1")) .then(logThen.bind(null, "2"));main();

    Logs

    日志

    Promise executor, result will be outerStart main[1] Promise then, result = outerIntermediate main[2] Promise then, result = outerEnd main

    Explanation

    说明

    This example involves all the rules!

    这个例子涉及所有规则!

    The main reason I included Example #4 was to set up this example :). Spec 6.2.3.1 tells us how await works; it’s fairly complicated to read through it all, but it boils down to the fact that await is mainly just syntactic sugar. For example, these two code blocks are analogous (they are not exactly equivalent, e.g. when using await you must use try/catch to handle rejected promises).

    我包含示例#4的主要原因是要设置此示例:)。 规范6.2.3.1告诉我们await如何工作。 阅读所有内容都相当复杂,但是归结为一个事实,即await主要是语法糖。 例如,这两个代码块是相似的(它们并不完全等效,例如,在使用await ,必须使用try / catch来处理被拒绝的Promise)。

    await foo(); // foo is an async function that returns a promiseconsole.log("hello");foo().then(() => { console.log("hello");});

    Credit for this example goes to jfriend00, see the original post here.

    此示例的 功劳归jfriend00所有 ,请参阅 此处 的原始帖子 。

    This means if we write main like this, it’s functionally equivalent.

    这意味着,如果我们这样写main ,它在功能上是等效的。

    const main = () => { console.log("Start main"); new Promise((resolve) => { resolve(); }).then(() => { console.log("Intermediate main"); new Promise((resolve) => { resolve(); }).then(() => { console.log("End main"); }); });};

    Further, instead of nesting the promises, we can flatten them out. If we do that, then the code looks exactly like Example #3! So if we understand how Promise.prototype.then() works, we should also be able to understand await.

    此外,我们可以嵌套承诺,而不是嵌套承诺。 如果我们这样做,那么代码看起来与示例#3完全一样! 因此,如果我们了解Promise.prototype.then()工作方式,我们也应该能够了解await 。

    Example#6 —再次等待 (Example #6 — Await, again)

    Code

    const func1 = async () => { console.log("Start func1"); await null; console.log("Intermediate func1, before calling func2"); func2(); console.log("Intermediate func1, after calling func2"); await null; console.log("End func1");};const func2 = async () => { console.log("Start func2"); await null; console.log("Intermediate func2"); await null; console.log("End func2");};func1();

    Logs

    日志

    Start func1Intermediate func1, before calling func2Start func2Intermediate func1, after calling func2Intermediate func2End func1End func2

    Explanation

    说明

    Again, this example involves all the rules.

    同样,此示例涉及所有规则。

    Example #5 was our first taste of async/await — this example will help us solidify the same concepts. Before, we said that these two code blocks are analogous:

    例#5是我们第一次尝试async / await -这个例子将帮助我们巩固相同的概念。 之前,我们说过这两个代码块是相似的:

    await foo(); // foo is an async function that returns a promiseconsole.log("hello");foo().then(() => { console.log("hello");});

    This means that you can think of of await in terms of Promise.prototype.then(), which is quite nice. This is actually all you need to know to understand how this example works. That is, you can rewrite this example like so.

    这意味着您可以根据Promise.prototype.then()来考虑await ,这非常不错。 这实际上是您了解该示例如何工作所需的全部知识。 也就是说,您可以像这样重写此示例。

    const func1Alt = () => { new Promise((resolve) => { console.log("Start func1"); resolve(); }) .then(() => { console.log("Intermediate func1, before calling func2"); func2Alt(); console.log("Intermediate func1, after calling func2"); }) .then(() => { console.log("End func1"); });};const func2Alt = () => { new Promise((resolve) => { console.log("Start func2"); resolve(); }) .then(() => { console.log("Intermediate func2"); }) .then(() => { console.log("End func2"); });};func1Alt();

    The output is be exactly the same, and understanding this just requires understanding Promise.prototype.then(). Nice!

    输出是完全相同的,理解这一点仅需要了解Promise.prototype.then() 。 真好!

    Some resources explain await differently, For example, MDN says the following:

    一些资源对await解释有所不同,例如, MDN表示以下内容 :

    An await can split execution flow, allowing the caller of the await's function to resume execution before the deferred continuation of the await's function. After the await defers the continuation of its function, if this is the first await executed by the function, immediate execution also continues by returning to the function's caller a pending Promise for the completion of the await's function and resuming execution of that caller.

    一个await可以分割执行流程,允许的主叫方await的功能恢复执行的延期延续之前await S功能“。 在await延迟其功能的继续之后,如果这是该功能执行的第一个await ,则立即执行还可以通过将未完成的Promise返回给函数的调用方来完成await功能并继续执行该调用方,从而继续执行。

    In the context of our example, this says that when the first await in func2 is hit, control flow returns to func1 (meaning Intermediate func1, after calling func2 will be logged), and the call to func2() in func1 returns a pending Promise. This makes sense, and it can be helpful to view the first await as returning control flow back to the caller, but I don’t think this is the best way to think about. Thinking about await in terms of Promise.prototype.then() is much more general, and lets you understand complicated scenarios fairly easily.

    在我们的示例上下文中,这表示当击中func2的第一个await时,控制流返回到func1 (这意味着Intermediate func1, after calling func2将记录Intermediate func1, after calling func2 ),并且对func1 func2()的func1将返回一个未决的Promise 。 这是有道理的,将第一次await视为将控制流返回给调用者可能会有所帮助,但是我认为这不是最好的考虑方法。 从Promise.prototype.then()角度考虑await更为普遍,使您可以轻松地理解复杂的场景。

    If you really want to know exactly how things are supposed to work, take a look at spec 6.2.3.1.

    如果您真的想确切了解事情应该如何工作,请查看规范6.2.3.1 。

    下次 (Next Time)

    That’s it for this post! It was quite long, but hopefully these examples are useful. Next time, I’ll cover how setTimeout fits into the picture, and hopefully touch on microtasks vs. macrotasks.

    就是这个帖子! 时间很长,但希望这些示例有用。 下次,我将介绍setTimeout如何适合图片,并希望介绍微任务与宏任务。

    资料来源 (Sources)

    https://stackoverflow.com/questions/46408228/es6-promise-execution-order-for-returned-values

    https://stackoverflow.com/questions/46408228/es6-promise-execution-order-for-returned-values

    https://stackoverflow.com/questions/36870467/what-is-the-order-of-execution-in-javascript-promises

    https://stackoverflow.com/questions/36870467/what-is-the-order-of-execution-in-javascript-promises

    https://stackoverflow.com/questions/63862842/in-javascript-in-what-order-are-then-handlers-executed

    https://stackoverflow.com/questions/63862842/in-javascript-in-what-order-are-then-handlers-exected

    https://javascript.info/microtask-queue

    https://javascript.info/microtask-queue

    翻译自: https://medium.com/swlh/order-of-execution-of-javascript-promises-with-examples-f2e8f81138b7

    qt5示例源程序执行不出

    Processed: 0.010, SQL: 9