Как определить порядок выполнения конструктора es6-prom? - PullRequest
0 голосов
/ 05 мая 2020

Рассмотрим следующий код.

(async () => {
    const values = {}
    const orders = []
    let promise = 0
    promise = new Promise(async resolve => {
        values[1] = promise
        orders.push(1)
        resolve(1)
        values[2] = promise
        orders.push(2)
        await new Promise(async r => {
            values[3] = await promise
            orders.push(3)
            setTimeout(r, 100)
        })
        values[4] = await promise
        orders.push(4)
        promise = 2
        values[5] = promise
        orders.push(5)
    })
    values[6] = await promise
    orders.push(6)
    await new Promise(resolve => setTimeout(resolve, 100)) // (*). try removing this line, result will change
    values[7] = await promise
    orders.push(7)
    console.log(values, orders)
})()

Вывод в консоль:

{ '1': 0, '2': 0, '3': 0, '4': 1, '5': 2, '6': 1, '7': 1 }
[ 1, 2, 3, 6, 4, 5, 7 ]

Мои вопросы:

  1. Есть ли в приведенный выше фрагмент, который является неопределенным поведением? Если нет, то после проверки результата меня смущает обещание ES6.

  2. Почему values[7] 1, а не 2? Обновление: с узлом v10.19.0 это 1. С nodev14.0.0, node-v12.10.0 и браузером это 2.

Обновление 2: повторение оценки с узлом v10 .19.0, после 20 значений [7] будет 1, один раз будет 2.

Если я удалю строку (*), результат изменится на следующий. Почему 4, 5 удалены?

{'1': 0, '2': 0, '3': 0, '6': 1, '7': 1} [1, 2, 3 , 6, 7]

Если у вас есть какое-либо практическое правило для такого рода выполнения, поделитесь, пожалуйста. Чем больше я пишу JS кода обещания, тем больше запутываюсь.

Дополнительные тесты здесь .

1 Ответ

1 голос
/ 05 мая 2020

Если есть что-то, в чем вы запутались, попробуйте свести это к просто к случаю, который вас смущает, а не ко всем другим случаям, что сказало ... мое лучшее предположение относительно того, что я думаю вы хотите знать:

  1. Функция-исполнитель (то, что вы передаете в new Promise()) вызывается немедленно, синхронно.
  2. Асинхронные c функции при вызове также выполняются немедленно. Они будут приостанавливаться только тогда, когда они нажимают первый await.
  3. Так что, если вы используете функцию asyn c, в которой нет await, вся функция asyn c будет выполняться синхронно, немедленно.
  4. Однако, даже если функция asyn c является «синхронной», она не вернется немедленно. Выполнение синхронно, но разрешение (обработка .then() listeners) будет в следующем тике).
...