ir3ne / javascript-questions-and-answers

🤓 A collection of JS questions about core concepts.
MIT License
6 stars 0 forks source link

What are the differences between microtasks and macrotasks in JavaScript? #9

Open ir3ne opened 4 days ago

travisliu commented 2 days ago

Understanding Microtasks vs. Macrotasks in JavaScript

When you're writing code in JavaScript, you might have to deal with how things happen in the background—which is called "asynchronous" behavior. JavaScript uses something called an event loop to manage how and when different parts of code get executed. The event loop decides the order in which things happen, and here is where we meet two important types of tasks: microtasks and macrotasks. Let’s explore the differences between them!

What Are Tasks in JavaScript?

To get the idea of microtasks and macrotasks, imagine JavaScript as a teacher managing a to-do list for a classroom. Some things are urgent and need to be taken care of quickly, while others can wait just a little longer. The event loop is like this teacher, deciding what gets done next. Microtasks and macrotasks are two kinds of "to-do" items that JavaScript has to handle.

What Are Macrotasks?

Macrotasks (sometimes just called "tasks") are bigger, and they represent things that take a bit more time or need to wait for something else to happen. Examples of macrotasks include events like setTimeout(), setInterval(), or user interactions like clicking a button. These tasks go into a queue called the task queue.

For example, if you tell JavaScript to wait for 1 second before running a piece of code (using setTimeout), that task goes into the macrotask queue. Once JavaScript finishes all the important work it’s doing, it will check the queue and handle the macrotask.

What Are Microtasks?

Microtasks are smaller and considered more urgent. They include things like promises (a way to handle asynchronous operations) and MutationObserver (used to monitor changes in the DOM—which is how web pages are structured). Microtasks go into a different queue called the microtask queue.

Microtasks always get priority over macrotasks. This means that whenever JavaScript is done with its current work, it will first check to see if there are any microtasks waiting before moving on to any macrotasks.

Imagine a teacher with a bunch of papers to grade: microtasks are like quick yes/no questions that need to be answered right away, while macrotasks are like full essays that the teacher can grade after those quick questions are handled.

How Does This Affect the Event Loop?

The event loop is responsible for deciding what JavaScript will do next. Here’s the usual order:

  1. JavaScript runs the current piece of code (like a function).
  2. It checks the microtask queue and handles everything there first.
  3. After all the microtasks are done, it moves on to the macrotask queue and handles the next macrotask.
  4. The event loop repeats this process over and over again.

This means that microtasks get priority and will run before macrotasks, even if the microtasks are added later. If a promise is resolved, JavaScript will make sure to handle that promise’s microtask before moving on to a macrotask, like executing code from setTimeout().

Example to Make It Clearer

Here’s a quick example to illustrate:

setTimeout(() => {
  console.log('This is a macrotask');
}, 0);

Promise.resolve().then(() => {
  console.log('This is a microtask');
});

console.log('This is regular code');

In this example, the output will be:

  1. This is regular code (the main synchronous code runs first).
  2. This is a microtask (because promises are microtasks and get handled before macrotasks).
  3. This is a macrotask (the setTimeout() is a macrotask, so it runs last).

Quick Summary

Understanding this difference helps when you're trying to figure out why some parts of your JavaScript code run before others—it's all about how the event loop manages microtasks and macrotasks!

ir3ne commented 1 day ago

thanks @travisliu! Could you open a PR for this?