This is the 11th day of my participation in the August More Text Challenge

Single threaded and asynchronous

  • Js is a single-threaded language that can only do one thing at a time
  • Browsers and NodeJS already support JS startupprocess, such as a web worker
  • Js and DOM rendering share the same thread because JS can modify the DOM structure
  • Do not get stuck when waiting (network request, scheduled task)
  • Need the asynchronous
  • Callback function form

Asynchronous usage scenario

  • Web requests, such as Ajax, image loading
  • A scheduled task, such as setTimeout

What is the difference between synchronous and asynchronous?

Based on the fact that JS is a single-threaded language, asynchrony does not block code execution, while synchronization does

Callback hell

Promise

Resolve callback hell, which can be chain-called

function getData(url){
   return new Promise((resolve,reject) = >{
       $.ajax({
           url,
           success(data){
               resolve(data)
           },
           error(err){
               reject(err)
           }
       })
   })
}
let url1 = '/data1.json'
let url2 = '/data2.json'
let url3 = '/data3.json'
getData(url1).then(data1= >{
   console.log(data1)
   return getData(url2) / / promise
}).then(data2= >{
   console.log(data2)
   return getData(url3)
}).then(data3= >{
   console.log(data3)
}).catch(err= >{
   console.error(err)
})
Copy the code

What are the three states of a Promise? How does it change?

  • Three states:pending resolved rejected
    • Pending -> Resolved or Pending -> Rejected
    • Irreversible change
  • The manifestation and change of state
    • Pending state, which does not trigger then and catch
    • Resolved state, which triggers subsequent THEN callbacks
    • The Rejected state triggers the subsequent catch callback
  • Effects of then and catch on state
    • Resolved then Return Rejected when the error message is returned
    • Catch return resolvedIf there is an error, return Rejected
//code 1
Promise.resolve().then(() = >{
    console.log(1)
}).catch(() = >{
    console.log(2)
}).then(() = >{
    console.log(3)})// return 1, 3

// code2
Promise.resolve().then(() = >{
    console.log(1) 
    throw new Error('error1')
}).catch(() = >{
    console.log(2)
}).then(() = >{
    console.log(3)})// Return 1, 2, 3

//code3
Promise.resolve().then(() = >{
    console.log(1) 
    throw new Error('error1')
}).catch(() = >{
    console.log(2)
}).catch(() = >{
    console.log(3)})// return 1, 2
Copy the code

Handwriting loads an image with a Promise

const url = 'https://inews.gtimg.com/newsapp_bt/0/11327712791/641' function loadImg(src){ return new Promise((resolve,reject)=>{ const img = document.createElement('img') img.onload = ()=>{ resolve(img) } img.onerror = ()=>{const err = new Error(' Error ${SRC} ') reject(err)} img.src = SRC})} loadImg(url). Then (img=>{const err = new Error(' Error ${SRC} ') reject(err)} img.src = SRC})} loadImg(url). Log (img.width) return img // common object}).then(img=>{console.log(img.height)}).catch(ex=>console.error(ex))Copy the code

Event loop Event loop or event polling

  • Js runs in a single thread
  • Asynchrony is implemented based on callbacks
  • The Event loop is how asynchronous callbacks are implemented

How is JS executed?

  • From front to back, line by line
  • If a line of execution fails, stop the execution of the following code
  • Execute synchronous code first, and then execute asynchronous code

The event loop process

  1. Synchronizes code and executes it line by line on the Call Stack
  2. In the case of asynchrony, it ‘records’ and waits for an opportunity (timing, network request, etc.).
  3. When the time is right, move to the Callback Queue
  4. If the Call Stack is empty (that is, the synchronized code is finished), the Event Loop starts working
  5. Search the Callback Queue and move it to the Call Stack if any exists
  6. And then continue to search (like perpetual motion machines)

DOM events and Event loops

  • Js is single threaded
  • Asynchronous (setTimeout, Ajax, etc.) uses callbacks, based on event loops
  • DOM events also use callbacks, based on event loops, rather than asynchronously

async/await

  • Asynchronous callback callback hell
  • Promise then catch chain calls, but also based on callback functions
  • Async /await is synchronous syntax and eliminates callback functions completely
// The loadImg method is shown above Promise! (async function(){
    // Syncing syntax
    
    const img1 = await loadImg(src1)
    console.log(img1.height,img1.width)
    
    const img2 = await loadImg(src2)
    console.log(img2.height,img2.width)
})()
Copy the code

Async /await and Promise relationship

  • Async /await is the ultimate weapon against asynchronous callbacks
  • Promise and Promise are not mutually exclusive
  • The two complement each other
  • Executes the async function and returns a Promise object
  • Await is equivalent to then of Promise
  • try... Catch catches exceptions instead of the catch of Promise
! (async function(){
   const p4 = Promise.reject('err1') / / rejected state
   
   const res = await p4  // await -> then
   console.log('res',res) / / does not perform
   
   try{
       const res = await p4
       consle.log(res)
   }catch(ex){
       console.log(ex) // try... Catch is equivalent to a promise catch
   }
   //err1}) ()Copy the code

Nature of asynchrony

  • Async /await is the ultimate weapon against asynchronous callbacks
  • Js is still single threaded, it still has to be asynchronous, and it has to be based on event loops
  • Async /await is just a syntactic sugar
  • 'await' can be treated as' callback '
async function fn(){
    return 100
}
!(async function(){
    const a = fn() // Promise
    const b= await fn() / / 100}) ()Copy the code
async function async1(){
    console.log('async1 start') / / 2
    await async2() //undefined
    Callback = async; callback = async; callback = async
    // Similarly, event loop,setTimeout(cb1)
    // setTimeout(function(){console.log('async1 end')})
    //Promise.resolve().then(()=> console.log('async1 end') )
    console.log('async1 end') / / 5
}
async function async2(){
    console.log('async2') / / 3
}
console.log('script start') / / 1
async1()
console.log('script end') / / 4
Copy the code
async function async1(){
    console.log('async1 start')  / / 2
    await async2() 
    
    // The following three lines are the contents of the asynchronous callback
    console.log('async1 end') / / 5
    await async3()
        // The next line is the content of the asynchronous callback
        console.log('async1 end2') / / 7
}
async function async2(){
    console.log('async2') / / 3
}
async function async3(){
    console.log('async3') / / 6
}
console.log('script start') / / 1
async1()
console.log('script end') //4 After the synchronization code is executed, the event loop is executed asynchronously
Copy the code

for … Of asynchronous traversal

  • for… In (and forEach for) is regular synchronous traversal
  • for… Of is often used for asynchronous traversal
function muti(num){
    return new Promise(resolve= >{
        setTimeout(() = >{
            resolve(num*num)
        },1000)})}const nums = [1.2.3]

nums.forEach(async(i)=>{
    const res =await muti(i)
    console.log(res) // One time output 1, 4, 9
})

!(async function(){
    for(let i of nums){
        const res =await muti(i)
        console.log(res) // Outputs 1, 4, 9 every 1s
    }
})()

Copy the code

MacroTash and microTask

What is a macro task? What are microtasks?

  • Macro task:SetTimeout, setInterval, Ajax, Dom events
  • Micro tasks:Promise, async/await
  • Microtasks are executed earlier than macro tasks

Event loop and DOM rendering

  • Js is single threaded and shares a thread with DOM rendering
  • While js is executing, some time is needed for DOM rendering

Execution order

  1. The Call Stack free
  2. Perform the current microtask
  3. Try DOM rendering
  4. Trigger Event loop

Why do microtasks execute earlier than macro tasks

  • Call Each time the Stack is cleared (that is, each poll ends), the synchronization task is complete
  • Both are opportunities to re-render the DOM, and re-render if the DOM structure changes
  • Then the next Event loop is triggered

Alert blocks JS execution as well as DOM rendering

The difference between microtasks and macro tasks

  • Macro task:Triggered after DOM renderingSuch as setTimeout; Is specified by the browser
  • Micro tasks:Triggered before DOM rendering, such as a Promise; ES6
async function async1(){
    console.log('async1 start') / / 2
    await async2()
    //await everything after that as callback content - microtasks
    console.log('async1 end') / / 6
}
async function async2(){
    console.log('async2') / / 3
}
console.log('script start') / / 1

setTimeout(function(){ / / macro task
    console.log('setTimeout') / / 8
},0)

async1()

// When a Promise is initialized, the function passed in is executed immediately
new Promise(function(resolve){
    console.log('promise1')  / / 4
    resolve()
}).then(function(){ Micro / / task
    console.log('promise2')  / / 7
})
console.log('script end') / / 5

// The event loop-Call stack is cleared.
// Perform microtasks
// (try to trigger DOM rendering)
// Trigger event loop to execute macro task

Copy the code