Непонятен порядок выполнения функций в js?

Ссылка скопирована
1 ответ
let data = [];          async function getData() {             let result = await fetch(' http://www.filltext.com/?rows=32&id={number|1000}&firstName={firstName}&lastName={lastName}&email={email}&phone={phone|(xxx)xxx-xx-xx}&address={addressObject}&description={lorem|32}');             if (result.ok) {                 data.push(...await result.json());             } else {                 throw new Error             }             console.log('1');         }          let id__header = document.querySelector('.id__header'),             firstName = document.querySelector('.firstName'),             lastName = document.querySelector('.lastName'),             email = document.querySelector('.email'),             phone = document.querySelector('.phone');          function createDataCells(arr) {             for (let i = 0; i < arr.length; i++) {                 id__header.insertAdjacentHTML('beforeend', `<div>${arr[i].id}</div>`);                 firstName.insertAdjacentHTML('beforeend', `<div>${arr[i].firstName}</div>`);                 lastName.insertAdjacentHTML('beforeend', `<div>${arr[i].lastName}</div>`);                 email.insertAdjacentHTML('beforeend', `<div>${arr[i].email}</div>`);                 phone.insertAdjacentHTML('beforeend', `<div>${arr[i].phone}</div>`);             }             console.log('2');         };              getData();              setTimeout(() => createDataCells(data), 0);

let data = []; async function getData() { let result = await fetch(' http://www.filltext.com/?rows=32&id={number|1000}&firstName={firstName}&lastName={lastName}&email={email}&phone={phone|(xxx)xxx-xx-xx}&address={addressObject}&description={lorem|32}'); if (result.ok) { data.push(...await result.json()); } else { throw new Error } console.log('1'); } let id__header = document.querySelector('.id__header'), firstName = document.querySelector('.firstName'), lastName = document.querySelector('.lastName'), email = document.querySelector('.email'), phone = document.querySelector('.phone'); function createDataCells(arr) { for (let i = 0; i < arr.length; i++) { id__header.insertAdjacentHTML('beforeend', `<div>${arr[i].id}</div>`); firstName.insertAdjacentHTML('beforeend', `<div>${arr[i].firstName}</div>`); lastName.insertAdjacentHTML('beforeend', `<div>${arr[i].lastName}</div>`); email.insertAdjacentHTML('beforeend', `<div>${arr[i].email}</div>`); phone.insertAdjacentHTML('beforeend', `<div>${arr[i].phone}</div>`); } console.log('2'); }; getData(); setTimeout(() => createDataCells(data), 0);

Почему createDataCells выполняется раньше getData, если getData это микрозадача, которая должна выполнится перед setTimeout

Дополнительно:

Ну например потому что JS не однопоточный, а getData асинхронная, т.е. идет в отдельном потоке (а не только отдельном от ui)
Поэтому не раньше. А просто параллельно
И естественно создать элементы в DOM куда быстрее чем что-то по сети делать
await используй

  • DogoWor, тогда для чего нужен await? Разве не для того чтобы ждать результата?
  • Suleymanov, для этого и нужен, но где? Он у тебя внутри getData, поэтому код внутри getData будет выполняться последовательно, а сам вызов getData идет без await, поэтому последовательно.

    Вероятно при попытке добавить await к главному вызову getData у тебя возникнет проблема - ты вызываешь getData не из асинхронной функции, а просто из главного контекста. В таком случае await использовать (почему-то) запрещено. Но ты можешь завернуть весь код в асинхронную функцию (я бы назвал ее main, по образцу точки входа в программах на Си) и вызвать main без async. Тогда все что внутри main, будет идти последовательно, сначала getData, потом тот таймаут. А если что-то добавить после этого вызова main, вне main, то оно будет идти параллельно. То есть await работает только на своем уровне вложенности.

  • DogoWor,

    Ну например потому что JS не однопоточный,

    https://www.geeksforgeeks.org/why-javascript-is-a-...
    https://russianblogs.com/article/6175476088/

  • DogoWor,

    Ну например потому что JS не однопоточный, а getData асинхронная, т.е. идет в отдельном потоке

    А такой жс с вами в одной комнате?

  • WbICHA, в основном, да, ошибка вышла. Можно сделать асинхронную функцию с каким-то долгим циклом, вызвать ее без await, а потом например сделать alert. Он сработает только тогда, когда цикл выполнится. Т.е. все, что находится в коде на JS, выполняется в одном потоке.
    Однако, функции самого языка, такие как fetch, могут спокойно выполняться в отдельных потоках, причем не в одном фоновом, а именно в нескольких отдельных. Это отличает его от "абсолютно однопоточного" Tarantool, где почти все функции и методы, в том числе самого языка и стандартной библиотеки (я про хранимки, которые пишутся на Lua), - блокирующие.
  • она и вызывается раньше, но т.к. в ней есть await, то окончание будет когда получится

    чтобы оно работало как нужно, можно сделать что-то типа getData().then(() => createDataCells(data));

    • Спасибо
    Нужно решить такую задачу?

    Опишите проблему, и специалист поможет с настройкой, исправлением ошибки или доработкой сайта. Подберём понятный план работ без лишней переписки.

    Заказать помощь
    Лучший ответ
    1
    Артём Dev Ответ

    Для понимания порядка выполнения функций в JavaScript, необходимо учитывать концепцию event loop и стек вызовов.

    Event loop - это механизм, который позволяет JavaScript выполнять асинхронный код. Когда код выполняется, он добавляется в стек вызовов. Если встречается асинхронная операция (например, setTimeout), она перемещается в очередь событий. После завершения выполнения кода в стеке, event loop проверяет очередь событий и добавляет соответствующий коллбэк в стек вызовов.

    Пример:

    console.log('1');
     
    setTimeout(() => {
      console.log('2');
    }, 0);
     
    console.log('3');

    console.log('1'); setTimeout(() => { console.log('2'); }, 0); console.log('3');

    В данном примере, будет выведено сначала '1', затем '3', и только после этого '2'. Это происходит потому, что setTimeout помещает колбэк в очередь событий, и он будет выполнен только после завершения текущего кода.

    Также важно помнить о том, что JavaScript - однопоточный язык программирования, что означает, что код выполняется последовательно. Если есть необходимость выполнять операции параллельно, можно использовать веб-воркеры или промисы.

    Надеюсь, данное объяснение поможет вам лучше понять порядок выполнения функций в JavaScript. Если у вас остались вопросы, не стесняйтесь задавать их.

    Другие ответы (0)

    Пока нет других ответов. Будьте первым, кто поможет автору.

    Ответить на вопрос

    комментарий

    Ваш адрес email не будет опубликован. Обязательные поля помечены *

    Вам также может быть интересно