Хорошо, поэтому я попытаюсь объяснить в соответствии с моим пониманием, я готов к обсуждению, и если я ошибаюсь, поправьте меня, пожалуйста:)
Так что в javascript есть только нить 1
. И давайте просто поговорим о синхронном коде. Javascript начнется с первой строки кода и начнет выполнение всего кода syn c, например console.log()
, airthmetic operations
et c.
Если он сталкивается с любым асинхронным кодом c как setTimeout
или promise
, он будет откладывать этот код до тех пор, пока не будет запущен другой фрагмент кода.
Например, когда вы вызываете add(1,2).then(fn)
, создается обещание и обратный вызов fn
из .then(fn)
зарегистрирован двигателем времени выполнения. Движок времени выполнения переместится на следующую строку после add()
и начнет выполнение любого синхронного кода. После выполнения всего синхронного кода будет вызван обратный вызов fn
, если обещание add()
разрешено.
Возьмем следующий пример:
function add(a, b) {
return new Promise(function(resolve, reject) {
resolve(a + b);
});
}
add(3, 6).then(v => {
throw new Error
});
while(1) {
console.log("")
}
После add()
называется, двигатель js движется к синхронному while
l oop. Теперь это бесконечно, в то время как l oop означает, что очередь никогда не опустеет для выполнения обратного вызова add()
обещания. Если бы это была многопоточная среда, обратный вызов add()
выполнялся бы во втором потоке, вызывая и Error и останавливая программу, которая никогда не происходит из-за одного потока.
Теперь взглянем на второй пример:
function add(a, b) {
return new Promise(function(resolve, reject) {
setTimeout(() => {
throw new Error
}, 1000)
});
}
add(3, 6).then(v => {
console.log(v)
});
while(1) {
console.log("")
}
Выполняя приведенный выше код, мы видим, что throw new Error никогда не вызывается, потому что наша программа снова застревает в бесконечности, пока l oop. Это означает, что код внутри обещания не выполняется (функция setTimeout
), потому что, если бы это был какой-либо второй поток, строка throw new Error
была бы названа остановкой программы. Механизм js создал обещание при вызове * 1034, отложил код обещания и перешел к следующей строке синхронного кода. Код внутри обещания будет вызван, когда очередь очистится, что в нашем примере никогда не произойдет из-за бесконечности, в то время как l oop.
Надеюсь, я имел смысл.