What gets logged?

Medium

Prompt

What gets logged when the following code is executed?

setTimeout(() => console.log(1));

Promise.resolve().then(() => console.log(2));

Promise.resolve().then(() =>
setTimeout(() => console.log(3))
);

new Promise(() => console.log(4));

setTimeout(() => console.log(5));

Solution

Fundamentally, this code is exploring how JavaScript handles different types of asynchronous operations. There are two key mechanisms at play here:

  • The task queue (also called the macrotask queue)
  • The microtask queue

Let's analyze the code step by step

setTimeout(() => console.log(1));
Promise.resolve().then(() => console.log(2));
Promise.resolve().then(() =>
setTimeout(() => console.log(3))
);
new Promise(() => console.log(4));
setTimeout(() => console.log(5));

First Pass: Synchronous Execution

  • Line 1: Schedules a callback that logs 1 to be executed later (adds to the macrotask queue)
  • Line 2: Creates a resolved Promise and schedules its .then() callback to log 2 (adds to the microtask queue)
  • Line 3: Creates another resolved Promise and schedules its .then() callback (adds to the microtask queue)
  • Line 4: Creates a new Promise and immediately executes its constructor function, which logs 4 (this is synchronous!)
  • Line 5: Schedules another callback that logs 5 to be executed later (adds to the macrotask queue)

So right away, we see 4 printed to the console.

Second Pass: After Synchronous Code Completes

Once the synchronous code is done, the JavaScript engine:

  • Processes all microtasks in the microtask queue
  • Then processes one macrotask from the macrotask queue
  • Returns to step 1 (check microtasks again)
  • Continues this cycle

So after the synchronous code, the microtask queue contains

  • A callback to log 2
  • A callback that will schedule a setTimeout to log 3

The macrotask queue contains

  • A callback to log 1
  • A callback to log 5

Processing the Microtask Queue

Now JavaScript processes all microtasks:

  • Executes the first microtask: logs 2
  • Executes the second microtask: schedules a new setTimeout that logs 3 (adds to the macrotask queue)

Processing the Macrotask Queue

After the microtask queue is empty, JavaScript processes the next macrotask:

  • Executes the first task from the queue: logs 1
  • Checks the microtask queue (it's empty)
  • Executes the next task from the macrotask queue: logs 5
  • Checks the microtask queue again (still empty)
  • Executes the last task from the macrotask queue: logs 3

So the final order of logs is 4 -> 2 -> 1 -> 5 -> 3

Final Output

4; // Immediate (synchronous) execution
2; // First microtask
1; // First macrotask
5; // Second macrotask
3; // Last macrotask (scheduled during microtask processing)

Here's what makes this interesting: JavaScript's event loop always prioritizes microtasks over macrotasks. This means Promise callbacks get processed before setTimeout callbacks, even if the setTimeout was scheduled first.

Think of it like having a VIP lane (microtasks) and a regular lane (macrotasks). JavaScript always serves everyone in the VIP lane before serving even one person from the regular lane.

This is why understanding the event loop is crucial for predicting how asynchronous code will execute in JavaScript.RetryClaude does not have the ability to run the code it generates yet.Claude can make mistakes. Please double-check responses.

00:00

Table of Contents