JavaScript Output Based Questions, with Answers
50 "what does this code print?" questions of the kind interviewers use to test the event loop, closures, this, hoisting and coercion. Read the code, write down the output, then open the answer.
They run from Easy to Hard. Each one links to a lesson that traces the code line by line, so a wrong guess shows you exactly where your model of JavaScript went off. More questions by level: for freshers and for experienced developers.
01 · JavaScript Fundamentals for Frontend Interviews · Easy
Primitive vs Reference Types
What is printed to the console when the following JavaScript code executes, and why does mutating a property behave differently than reassigning the parameter?
let primitiveVal = 42; let objA = { count: 1 }; let objB = objA; function update(num, target) { num = 100; target.count = 5; target = { count: 999 }; } update(primitiveVal, objA); console.log(primitiveVal, objA.count, objB.count);Why it prints this, traced line by lineShow the output
42 5 502 · JavaScript Fundamentals for Frontend Interviews · Medium
Type Coercion & Equality
What is the exact output printed to the console when evaluating the following statements in standard ECMAScript?
const res1 = 1 + '2' + 3; const res2 = 4 - '2' + '1'; const res3 = [] == ![]; const res4 = [1, 2] + [3, 4]; console.log(res1, res2, res3, res4);Why it prints this, traced line by lineShow the output
'123' '21' true '1,23,4'03 · JavaScript Fundamentals for Frontend Interviews · Medium
Scope, Hoisting & TDZ
What is printed to the console when the following snippet executes, and why does bar() behave differently than foo()?
console.log(typeof nonExistent); console.log(typeof hoistedVar); var hoistedVar = 10; function testScope() { console.log(hoistedVar); var hoistedVar = 20; console.log(hoistedVar); } testScope();Why it prints this, traced line by lineShow the output
'undefined' 'undefined' undefined 2004 · JavaScript Fundamentals for Frontend Interviews · Medium
Objects, Arrays & Reference Semantics
What is logged to the console when the following code executes, and how do object aliasing and shallow copying affect nested property mutation?
const original = { id: 1, tags: ['js', 'web'], meta: { views: 100 }, }; const shallowCopy = { ...original }; const alias = original; shallowCopy.id = 2; shallowCopy.tags.push('v8'); shallowCopy.meta.views += 50; alias.id = 3; const res1 = original.id; const res2 = original.tags.length; const res3 = original.meta.views; const res4 = original === shallowCopy; const res5 = original.meta === shallowCopy.meta; console.log(res1, res2, res3, res4, res5);Why it prints this, traced line by lineShow the output
3 3 150 false true05 · JavaScript Fundamentals for Frontend Interviews · Medium
Equality, Coercion & Comparison Traps
What is logged to the console when the following equality and relational comparisons execute, and why do loose equality and relational operators handle null and arrays with fundamentally different rules?
const c1 = null >= 0; const c2 = null == 0; const c3 = '12' < '9'; const c4 = Object.is(NaN, NaN); const c5 = Object.is(+0, -0); const c6 = [0] == false; console.log(c1, c2, c3, c4, c5, c6);Why it prints this, traced line by lineShow the output
true false true true false true06 · Execution Contexts, Closures, and Object Prototypes · Medium
Execution Context & Call Stack
What is the exact logged output when the following JavaScript code executes, and how does the V8 call stack transition through each function invocation and return?
function first() { console.log('first:start'); second(); console.log('first:end'); } function second() { console.log('second:start'); third(); console.log('second:end'); } function third() { console.log('third:exec'); } first();Why it prints this, traced line by lineShow the output
first:start second:start third:exec second:end first:end07 · Execution Contexts, Closures, and Object Prototypes · Medium
Closures & Lexical Scope
What is printed to the console when the following timer function executes, and how does JavaScript closure scoping determine the printed numbers?
function runTimers() { for (var i = 0; i < 3; i++) { setTimeout(function() { console.log('var:', i); }, 10); } for (let j = 0; j < 3; j++) { setTimeout(function() { console.log('let:', j); }, 10); } } runTimers();Why it prints this, traced line by lineShow the output
var: 3 (x3), let: 0, 1, 208 · Execution Contexts, Closures, and Object Prototypes · Medium
this, call, apply & bind
What is printed to the console when the following JavaScript code executes, and how do explicit binding and arrow functions alter the value of 'this'?
const obj = { name: 'Alice', regular() { return this.name; }, getArrow() { return () => this.name; }, }; const bob = { name: 'Bob' }; const charlie = { name: 'Charlie' }; const extracted = obj.regular; const bound = obj.regular.bind(bob); const nestedArrow = obj.getArrow(); console.log( obj.regular(), extracted.call(charlie), bound.call(charlie), nestedArrow.call(charlie) );Why it prints this, traced line by lineShow the output
Alice Charlie Bob Alice09 · Execution Contexts, Closures, and Object Prototypes · Medium
Prototypes & Inheritance
What is logged to the console when the following code executes, and how does property deletion interact with shadowed prototype properties?
function Device(brand) { this.brand = brand; } Device.prototype.category = 'electronics'; Device.prototype.battery = 100; const phone = new Device('Acme'); phone.battery = 85; const res1 = phone.battery; delete phone.battery; const res2 = phone.battery; delete phone.category; const res3 = phone.category; const res4 = phone.hasOwnProperty('battery'); const res5 = 'battery' in phone; console.log(res1, res2, res3, res4, res5);Why it prints this, traced line by lineShow the output
85 100 electronics false true10 · Execution Contexts, Closures, and Object Prototypes · Medium
Property Flags & Descriptors
What is logged to the console when the following code executes, and how do Object.defineProperty descriptor defaults affect enumeration, mutation, and deletion?
const obj = {}; Object.defineProperty(obj, 'id', { value: 101, // writable, enumerable, configurable omitted }); obj.title = 'Widget'; const keys = Object.keys(obj); obj.id = 999; const deleteId = delete obj.id; const ownNames = Object.getOwnPropertyNames(obj); console.log(keys.join(','), obj.id, deleteId, ownNames.join(','));Why it prints this, traced line by lineShow the output
title 101 false id,title11 · The Event Loop, Microtasks, and Asynchronous Concurrency · Medium
Promises & Chaining
What output is logged to the console when the following promise chain executes, and how do errors propagate through .catch() and .finally()?
const results = []; Promise.resolve('start') .then((val) => { results.push(val); throw new Error('fail'); }) .then(() => { results.push('unreachable'); }) .catch((err) => { results.push('caught: ' + err.message); return 'recovered'; }) .finally(() => { results.push('cleanup'); return 'ignored'; }) .then((val) => { results.push('end: ' + val); console.log(results.join(' -> ')); });Why it prints this, traced line by lineShow the output
start -> caught: fail -> cleanup -> end: recovered12 · The Event Loop, Microtasks, and Asynchronous Concurrency · Medium
async/await Internals
What is the exact sequence of outputs printed to the console when the following JavaScript code executes, and how do async/await suspension cycles interleave with Promise.then() microtasks?
async function main() { console.log('1'); await null; console.log('2'); await Promise.resolve(); console.log('3'); } console.log('A'); main(); console.log('B'); Promise.resolve() .then(() => { console.log('C'); }) .then(() => { console.log('D'); }); console.log('E');Why it prints this, traced line by lineShow the output
A 1 B E 2 C 3 D13 · The Event Loop, Microtasks, and Asynchronous Concurrency · Medium
Promise Combinators (all, allSettled, race, any)
What is logged to the console when the four Promise combinators execute with a rejected and a resolved promise, and how do their fulfillment and rejection rules diverge?
async function runCombinators() { const p1 = Promise.reject('E1'); const p2 = Promise.resolve('OK'); const res1 = await Promise.all([p1, p2]).catch((e) => `all:${e}`); const res2 = await Promise.any([p1, p2]).then((v) => `any:${v}`); const res3 = await Promise.race([p1, p2]).catch((e) => `race:${e}`); const res4 = await Promise.allSettled([p1, p2]).then((s) => `settled:${s.map((x) => x.status).join(',')}` ); console.log([res1, res2, res3, res4].join(' ')); } runCombinators();Why it prints this, traced line by lineShow the output
all:E1 any:OK race:E1 settled:rejected,fulfilled14 · The Event Loop, Microtasks, and Asynchronous Concurrency · Medium
Timers & Concurrency Control
What is logged to the console when the following timer and microtask scheduling code executes, and how does the event loop interleave microtasks created inside a macrotask callback before processing subsequent macrotasks?
const order = []; order.push('sync-1'); setTimeout(() => { order.push('timer-1'); Promise.resolve().then(() => order.push('micro-after-t1')); }, 0); setTimeout(() => { order.push('timer-2'); console.log(order.join(' ')); }, 0); Promise.resolve().then(() => { order.push('micro-1'); queueMicrotask(() => order.push('micro-2')); }); order.push('sync-2');Why it prints this, traced line by lineShow the output
sync-1 sync-2 micro-1 micro-2 timer-1 micro-after-t1 timer-215 · Tricky JavaScript Output Prediction & Code Reasoning · Medium
Hoisting & Scope Traps
What is logged to the console when the following functions execute, and how do parameter scoping, function declaration precedence, and loop variable hoisting resolve?
var x = 10; function parameterScope(a = x) { var x = 20; return a; } function declarationPrecedence() { var before = typeof entity; function entity() {} var entity = 'reassigned'; return before + ' ' + typeof entity; } var b = 1; for (var b = 0; b < 3; b++) {} console.log(parameterScope(), declarationPrecedence(), b);Why it prints this, traced line by lineShow the output
10 function string 316 · JavaScript Utility Implementations and Standard Polyfills · Medium
Debounce and Throttle Implementations
What is logged to the console when the following code executes, and how do debounce cancellation and leading-edge throttling alter callback dispatch order?
function debounce(fn, delay) { let timerId = null; return function (...args) { if (timerId) clearTimeout(timerId); timerId = setTimeout(() => { fn.apply(this, args); timerId = null; }, delay); }; } function throttle(fn, limit) { let inThrottle = false; return function (...args) { if (!inThrottle) { fn.apply(this, args); inThrottle = true; setTimeout(() => { inThrottle = false; }, limit); } }; } const logs = []; const logPush = (msg) => logs.push(msg); const debounced = debounce((v) => logPush(`deb:${v}`), 50); const throttled = throttle((v) => logPush(`thr:${v}`), 50); throttled('1'); throttled('2'); debounced('A'); debounced('B'); logPush('sync-end'); setTimeout(() => { console.log(logs.join(' ')); }, 100);Why it prints this, traced line by lineShow the output
thr:1 sync-end deb:B17 · JavaScript Utility Implementations and Standard Polyfills · Medium
Flattening Nested Arrays
What is logged to the console when Array.prototype.flat() is executed on deeply nested and sparse arrays, and how does the native flattening algorithm handle uninitialized empty slots?
const nested = [1, [2, [3, [4]]]]; const res1 = nested.flat(1); const res2 = nested.flat(Infinity); const sparse = [1, , 3]; const res3 = sparse.flat(); console.log( res1.length, res2.join('-'), res3.length, 1 in sparse );Why it prints this, traced line by lineShow the output
3 1-2-3-4 2 false18 · JavaScript Utility Implementations and Standard Polyfills · Medium
Higher-Order Functions & Currying
What is logged to the console when the following code executes, and how does the execution order differ between pipe() and compose()?
const add = (a) => (b) => a + b; const multiply = (a) => (b) => a * b; const addFive = add(5); const double = multiply(2); const pipe = (...fns) => (x) => fns.reduce((v, f) => f(v), x); const compose = (...fns) => (x) => fns.reduceRight((v, f) => f(v), x); const pipeline = pipe(addFive, double); const composed = compose(addFive, double); const res1 = add(3)(4); const res2 = pipeline(10); const res3 = composed(10); console.log(res1, res2, res3);Why it prints this, traced line by lineShow the output
7 30 2519 · JavaScript Utility Implementations and Standard Polyfills · Medium
JavaScript Array Methods
What is logged to the console when the following JavaScript code executes, and how do missing return statements and method return values affect the outcome?
const nums = [1, 2, 3, 4]; const mapped = nums.map((n) => { if (n % 2 === 0) return n * 2; }); const filtered = nums.filter((n) => { n > 1; }); const reduced = [1, 2, 3].reduce((acc, curr) => acc + curr, 10); const list = [1, 2]; const forEachRet = list.forEach((n, i, arr) => { arr[i] = n * 10; }); console.log( mapped.join(','), filtered.length, reduced, String(forEachRet), list.join(',') );Why it prints this, traced line by lineShow the output
,4,,8 0 16 undefined 10,2020 · Browser APIs, DOM Performance, and Client-Side Security · Medium
DOM Traversal & Reflow
What is logged to the console when the following DOM element and fragment manipulation operations execute, and how do childNodes versus children and DocumentFragment insertions affect tree structure?
const parent = document.createElement('div'); parent.innerHTML = '<span>A</span><!-- comment --><p>B</p>'; const childNodesCount = parent.childNodes.length; const childrenCount = parent.children.length; const span = parent.children[0]; const closestDiv = span.closest('div') === parent; const fragment = document.createDocumentFragment(); fragment.appendChild(document.createElement('section')); parent.appendChild(fragment); const finalChildren = parent.children.length; console.log(childNodesCount, childrenCount, closestDiv, finalChildren);Why it prints this, traced line by lineShow the output
3 2 true 321 · Browser APIs, DOM Performance, and Client-Side Security · Medium
Web Storage, Cookies & Persistence
What is logged to the console when the following Web Storage operations execute, and how do implicit string coercion and serialization dictate stored types?
class StorageMock { constructor() { this.store = new Map(); } setItem(k, v) { this.store.set(String(k), String(v)); } getItem(k) { const val = this.store.get(String(k)); return val !== undefined ? val : null; } } const storage = new StorageMock(); // 1. Storing object without serialization storage.setItem('user', { id: 1 }); const rawUser = storage.getItem('user'); // 2. Storing number and boolean storage.setItem('count', 42); storage.setItem('active', false); const countType = typeof storage.getItem('count'); const activeVal = storage.getItem('active'); // 3. Proper JSON serialization storage.setItem('session', JSON.stringify({ token: 'xyz' })); const parsedToken = JSON.parse(storage.getItem('session')).token; console.log(rawUser, countType, activeVal, parsedToken);Why it prints this, traced line by lineShow the output
[object Object] string false xyz22 · Modern JavaScript: ES Modules, Iterators, and Weak Collections · Medium
JavaScript Modules (ESM vs CommonJS)
What is printed to the console when the following code executes, and how does the live binding model of ES Modules contrast with CommonJS value exports?
const esmExport = (() => { let counter = 10; return { get counter() { return counter; }, increment() { counter += 5; }, }; })(); const cjsExport = (() => { let counter = 10; return { counter, increment() { counter += 5; }, }; })(); const beforeESM = esmExport.counter; const beforeCJS = cjsExport.counter; esmExport.increment(); cjsExport.increment(); const afterESM = esmExport.counter; const afterCJS = cjsExport.counter; console.log(beforeESM, beforeCJS, afterESM, afterCJS);Why it prints this, traced line by lineShow the output
10 10 15 1023 · Modern JavaScript: ES Modules, Iterators, and Weak Collections · Medium
Iterators & Generators
What is logged to the console when the generator is driven step-by-step with next(), and how do yield argument injection and iterator exhaustion operate?
function* stepSequence(start) { const step1 = yield start * 2; const step2 = yield (step1 || 1) + 10; return 'DONE'; } const gen = stepSequence(5); const v1 = gen.next().value; const v2 = gen.next(20).value; const r3 = gen.next(); const v3 = r3.value; const v4 = gen.next().value; console.log(v1, v2, v3, String(v4));Why it prints this, traced line by lineShow the output
10 30 DONE undefined24 · Modern JavaScript: ES Modules, Iterators, and Weak Collections · Medium
Maps, Sets, WeakMap & WeakSet
What is logged to the console when the following Map and Set operations execute, and how do object reference identity and SameValueZero equality determine collection size and retrieval?
const map = new Map(); const set = new Set(); const keyObj = { id: 1 }; map.set(keyObj, 'original'); map.set({ id: 1 }, 'duplicate?'); map.set(NaN, 'first-nan'); map.set(NaN, 'second-nan'); set.add(keyObj); set.add({ id: 1 }); set.add(NaN); set.add(NaN); const res1 = map.size; const res2 = set.size; const res3 = map.get(keyObj); const res4 = map.get({ id: 1 }); console.log(res1, res2, res3, String(res4));Why it prints this, traced line by lineShow the output
3 3 original undefined25 · Modern JavaScript: ES Modules, Iterators, and Weak Collections · Medium
JavaScript Classes & Inheritance
What is logged to the console when the following class hierarchy executes, and how do static inheritance, private fields, and prototype enumerability operate?
class Vehicle { #fuel = 100; static count = 0; constructor(brand) { this.brand = brand; Vehicle.count++; } getFuel() { return this.#fuel; } static getCount() { return this.count; } } class Car extends Vehicle { constructor(brand, doors = 4) { super(brand); this.doors = doors; } getDetails() { return this.brand + '-' + this.doors + '-' + this.getFuel(); } } const c1 = new Car('Tesla', 2); const res1 = c1.getDetails(); const res2 = Car.getCount(); const res3 = Object.keys(Car.prototype).length; const res4 = c1 instanceof Vehicle; console.log(res1, res2, res3, res4);Why it prints this, traced line by lineShow the output
Tesla-2-100 1 0 true26 · Modern JavaScript: ES Modules, Iterators, and Weak Collections · Medium
Tagged Templates & Frontend Security
What is logged to the console when the following safeHtml tagged template function processes an untrusted user payload and a role string containing special characters?
function escapeHtml(str) { return String(str) .replace(/&/g, '&') .replace(/</g, '<') .replace(/>/g, '>') .replace(/"/g, '"') .replace(/'/g, '''); } function safeHtml(strings, ...values) { return strings.reduce((acc, str, i) => { const val = i < values.length ? escapeHtml(values[i]) : ''; return acc + str + val; }, ''); } const user = '<img src=x onerror=alert(1)>'; const role = 'Admin & Lead'; const safe = safeHtml`<span>User: ${user} (${role})</span>`; const hasRawTag = safe.includes('<img'); const hasEscapedTag = safe.includes('<img'); const hasEscapedAmp = safe.includes('&'); console.log(hasRawTag, hasEscapedTag, hasEscapedAmp);Why it prints this, traced line by lineShow the output
false true true27 · Debugging, Memory Leak Analysis, and Code Quality · Medium
Error Handling & Debugging
What is logged to the console when the following code executes, and why does returning inside a finally block override previous return statements?
function processData(val) { try { if (val < 0) { throw new RangeError('Must be positive'); } return val * 2; } catch (err) { if (err instanceof RangeError) { return 'handled-range'; } throw err; } } function computeWithFinally() { try { throw new Error('fail'); } catch (err) { return 'from-catch'; } finally { return 'from-finally'; } } const res1 = processData(5); const res2 = processData(-1); const res3 = computeWithFinally(); console.log(res1, res2, res3);Why it prints this, traced line by lineShow the output
10 handled-range from-finally28 · JavaScript Fundamentals for Frontend Interviews · Hard
Memory Management & Garbage Collection
What is logged to the console when the following object reference graph is mutated, and why do circular references remain reachable as long as an active path from a root exists?
let parent = { name: 'parent' }; let child = { name: 'child' }; // 1. Establish circular references parent.child = child; child.parent = parent; // 2. Break root reference to parent const childRef = parent.child; parent = null; // 3. Inspect reachability through childRef const res1 = childRef.name; const res2 = childRef.parent ? childRef.parent.name : null; const res3 = childRef.parent.child === childRef; console.log(res1, res2, res3);Why it prints this, traced line by lineShow the output
child parent true29 · The Event Loop, Microtasks, and Asynchronous Concurrency · Hard
Event Loop & Microtasks
What is the exact order of numbers printed to the console when the following JavaScript snippet executes?
console.log(1); setTimeout(() => { console.log(2); }, 0); Promise.resolve() .then(() => { console.log(3); return Promise.resolve(4); }) .then((val) => { console.log(val); }); queueMicrotask(() => { console.log(5); }); console.log(6);Why it prints this, traced line by lineShow the output
1 6 3 5 4 230 · The Event Loop, Microtasks, and Asynchronous Concurrency · Hard
Promise Concurrency Pool
What is logged to the console when the following promisePool utility executes four tasks with variable delays under a concurrency limit of 2?
async function promisePool(tasks, limit) { const results = []; const executing = new Set(); let peak = 0; for (const [index, task] of tasks.entries()) { const p = Promise.resolve().then(task).then((res) => { results[index] = res; executing.delete(p); }); executing.add(p); peak = Math.max(peak, executing.size); if (executing.size >= limit) { await Promise.race(executing); } } await Promise.all(executing); return { results, peak }; } async function run() { const logs = []; const delayTask = (id, ms) => () => new Promise((resolve) => setTimeout(() => { logs.push('done:' + id); resolve(id * 10); }, ms) ); const tasks = [ delayTask(1, 30), delayTask(2, 10), delayTask(3, 20), delayTask(4, 10) ]; const { results, peak } = await promisePool(tasks, 2); console.log(logs.join(' ') + ' | peak:' + peak + ' | res:' + results.join(',')); } run();Why it prints this, traced line by lineShow the output
done:2 done:1 done:3 done:4 | peak:2 | res:10,20,30,4031 · The Event Loop, Microtasks, and Asynchronous Concurrency · Hard
Async Iterators & Streaming Backpressure
What is logged to the console when the following async generator pipeline is consumed with for await...of and terminated early via a break statement?
let cleanedUp = false; async function* generateChunks(count) { try { for (let i = 1; i <= count; i++) { yield Promise.resolve(i * 10); } } finally { cleanedUp = true; } } async function processStream() { const received = []; for await (const chunk of generateChunks(5)) { received.push(chunk); if (chunk === 30) { break; } } return { received, cleanedUp }; } processStream().then(({ received, cleanedUp }) => { console.log(received.join(','), cleanedUp); });Why it prints this, traced line by lineShow the output
10,20,30 true32 · Tricky JavaScript Output Prediction & Code Reasoning · Hard
this Context Traps
What is logged to the console when the following object methods, arrow functions, and bound functions are invoked, and why does chained binding preserve the original target context?
const user = { id: 'master', getId() { return this.id; }, getNested() { const inner = () => this.id; return inner(); } }; const boundA = user.getId.bind({ id: 'worker' }); const boundB = boundA.bind({ id: 'guest' }); const res1 = user.getId(); const res2 = user.getNested(); const res3 = boundB(); const res4 = boundA.call({ id: 'admin' }); console.log(res1, res2, res3, res4);Why it prints this, traced line by lineShow the output
master master worker worker33 · Tricky JavaScript Output Prediction & Code Reasoning · Hard
Async Execution Ordering
What is logged to the console when the following code executes, and how do async/await expressions interleave with chained Promise.then callbacks and timer macrotasks?
const log = []; log.push('1'); setTimeout(() => { log.push('2'); console.log(log.join(' ')); }, 0); async function asyncFn() { log.push('3'); await null; log.push('4'); } asyncFn(); new Promise((resolve) => { log.push('5'); resolve(); }) .then(() => { log.push('6'); }) .then(() => { log.push('7'); }); log.push('8');Why it prints this, traced line by lineShow the output
1 3 5 8 4 6 7 234 · Tricky JavaScript Output Prediction & Code Reasoning · Hard
Coercion & Mutation Traps
What is logged to the console when the following object property indexing, array parameter mutation, and primitive coercion expressions execute?
const a = {}; const b = { key: 'b' }; const c = { key: 'c' }; a[b] = 123; a[c] = 456; const arr = [1, 2, 3]; function mutate(list, item) { list.push(item); list = [99]; list.push(100); } mutate(arr, 4); const res1 = a[b]; const res2 = arr.length; const res3 = [] + {}; const res4 = (null == undefined) + '-' + (null === undefined); console.log(res1, res2, res3, res4);Why it prints this, traced line by lineShow the output
456 4 [object Object] true-false35 · JavaScript Utility Implementations and Standard Polyfills · Hard
Memoize and Cache Layer
What is logged to the console when the following memoized functions are invoked, and how do default JSON argument serialization versus custom key resolvers determine cache hit rates?
function memoize(fn, resolver) { const cache = new Map(); return function (...args) { const key = resolver ? resolver(...args) : JSON.stringify(args); if (cache.has(key)) { return { value: cache.get(key), cached: true }; } const result = fn.apply(this, args); cache.set(key, result); return { value: result, cached: false }; }; } let calls = 0; const add = (a, b) => { calls++; return a + b; }; const defaultMem = memoize(add); const customMem = memoize(add, (a, b) => [a, b].sort().join(',')); const r1 = defaultMem(1, 2); const r2 = defaultMem(1, 2); const r3 = defaultMem(2, 1); const r4 = customMem(1, 2); const r5 = customMem(2, 1); console.log(calls, r1.cached, r2.cached, r3.cached, r5.cached);Why it prints this, traced line by lineShow the output
3 false true false true36 · JavaScript Utility Implementations and Standard Polyfills · Hard
Retry with Exponential Backoff & Jitter
What is logged to the console when the following retry utility executes against an API that fails twice with 503 errors before succeeding, using an injected deterministic sleep provider?
async function retryWithBackoff(fn, options = {}) { const { maxRetries = 3, baseDelay = 100, shouldRetry = () => true, sleep = (ms) => new Promise(r => setTimeout(r, ms)) } = options; let attempt = 0; while (true) { try { return await fn(attempt); } catch (err) { attempt++; if (attempt > maxRetries || !shouldRetry(err)) { throw err; } const delay = baseDelay * (2 ** (attempt - 1)); await sleep(delay); } } } const delays = []; const mockSleep = (ms) => { delays.push(ms); return Promise.resolve(); }; let callCount = 0; const flakeyApi = async (attempt) => { callCount++; if (callCount < 3) { const err = new Error('503 Service Unavailable'); err.status = 503; throw err; } return 'SUCCESS'; }; const isRetryable = (err) => err.status >= 500; retryWithBackoff(flakeyApi, { maxRetries: 3, baseDelay: 50, shouldRetry: isRetryable, sleep: mockSleep }) .then((result) => { console.log(result, callCount, delays.join(',')); });Why it prints this, traced line by lineShow the output
SUCCESS 3 50,10037 · Browser APIs, DOM Performance, and Client-Side Security · Hard
IntersectionObserver & List Virtualization
What is logged to the console when the following framework-independent list virtualization window calculation executes for a dataset of 1,000 items with overscan buffering?
function computeVirtualWindow({ total, itemHeight, viewportHeight, scrollTop, overscan = 1 }) { if (total === 0) return { totalHeight: 0, startIndex: 0, endIndex: -1, visibleCount: 0, offsetY: 0 }; const totalHeight = total * itemHeight; const rawStart = Math.floor(scrollTop / itemHeight); const visibleCapacity = Math.ceil(viewportHeight / itemHeight); const rawEnd = rawStart + visibleCapacity - 1; const startIndex = Math.max(0, rawStart - overscan); const endIndex = Math.min(total - 1, rawEnd + overscan); const visibleCount = endIndex >= startIndex ? endIndex - startIndex + 1 : 0; const offsetY = startIndex * itemHeight; return { totalHeight, startIndex, endIndex, visibleCount, offsetY }; } const win = computeVirtualWindow({ total: 1000, itemHeight: 40, viewportHeight: 200, scrollTop: 120, overscan: 1, }); console.log(win.totalHeight, win.startIndex, win.endIndex, win.visibleCount, win.offsetY);Why it prints this, traced line by lineShow the output
40000 2 8 7 8038 · Browser APIs, DOM Performance, and Client-Side Security · Hard
Web Workers & Transferable Objects
What is logged to the console when the following snippet demonstrates structured cloning versus zero-copy memory ownership transfer with ArrayBuffers, and why does the source buffer become detached?
const regularObj = { data: [1, 2, 3] }; const clonedObj = structuredClone(regularObj); clonedObj.data.push(4); const sourceBuffer = new ArrayBuffer(16); const viewBefore = new Uint8Array(sourceBuffer); viewBefore[0] = 99; const transferPayload = structuredClone( { payload: sourceBuffer }, { transfer: [sourceBuffer] } ); const isDetached = sourceBuffer.byteLength === 0; const destLength = transferPayload.payload.byteLength; const destVal = new Uint8Array(transferPayload.payload)[0]; console.log(regularObj.data.length, clonedObj.data.length, isDetached, destLength, destVal);Why it prints this, traced line by lineShow the output
3 4 true 16 9939 · Modern JavaScript: ES Modules, Iterators, and Weak Collections · Hard
Symbols & Metaprogramming
What is logged to the console when local vs global symbols are compared, an object with a symbol key and Symbol.toPrimitive hook is inspected via reflection, and type coercions execute?
const s1 = Symbol('id'); const s2 = Symbol('id'); const s3 = Symbol.for('shared'); const s4 = Symbol.for('shared'); const user = { name: 'Alex', [s1]: 101, [Symbol.toPrimitive](hint) { if (hint === 'number') return 42; if (hint === 'string') return 'User:Alex'; return 'Alex-default'; } }; const keysCount = Object.keys(user).length; const ownKeysCount = Reflect.ownKeys(user).length; const isSameGlobal = s3 === s4; const isSameLocal = s1 === s2; const numCoercion = +user; const strCoercion = `${user}`; console.log( keysCount, ownKeysCount, isSameGlobal, isSameLocal, numCoercion, strCoercion );Why it prints this, traced line by lineShow the output
1 3 true false 42 User:Alex40 · Modern JavaScript: ES Modules, Iterators, and Weak Collections · Hard
Proxy and Reflect Metaprogramming
What is logged to the console when the following Proxy and Reflect operations execute across get, set, has, and deleteProperty traps?
const target = { name: 'Alice', age: 28, _secret: 'shh' }; const logs = []; const handler = { get(t, prop, receiver) { if (prop === 'tier') return 'Gold'; return Reflect.get(t, prop, receiver); }, set(t, prop, val, receiver) { if (prop === 'age' && (typeof val !== 'number' || val < 0)) { logs.push('invalid-age'); return false; } return Reflect.set(t, prop, val, receiver); }, has(t, prop) { if (typeof prop === 'string' && prop.startsWith('_')) return false; return Reflect.has(t, prop); }, deleteProperty(t, prop) { if (prop === 'name') { logs.push('cant-delete'); return false; } return Reflect.deleteProperty(t, prop); } }; const proxy = new Proxy(target, handler); logs.push(proxy.tier); proxy.age = -5; proxy.age = 30; logs.push(proxy.age); logs.push('_secret' in proxy); delete proxy.name; logs.push(proxy.name); console.log(logs.join(' '));Why it prints this, traced line by lineShow the output
Gold invalid-age 30 false cant-delete Alice41 · Debugging, Memory Leak Analysis, and Code Quality · Hard
Memory Leaks & V8 GC
What is logged to the console when an object is tracked in a root collection, its local variable binding is reassigned to null, and it is subsequently detached from the collection root?
class MemoryTracker { constructor() { this.retainedRoots = new Set(); } attach(obj) { this.retainedRoots.add(obj); } detach(obj) { this.retainedRoots.delete(obj); } isReachable(obj) { return this.retainedRoots.has(obj); } } const tracker = new MemoryTracker(); let detachedDiv = { tag: 'div', id: 'dialog' }; tracker.attach(detachedDiv); const ref1 = tracker.isReachable(detachedDiv); const originalRef = detachedDiv; detachedDiv = null; const ref2 = tracker.isReachable(originalRef); tracker.detach(originalRef); const ref3 = tracker.isReachable(originalRef); console.log(ref1, ref2, ref3, detachedDiv === null);Why it prints this, traced line by lineShow the output
true true false true42 · Connecting JavaScript Runtime Mechanics to React Internals · Hard
Closures & Stale State in React
What is logged to the console when the following runtime simulation executes direct state updates, functional state updaters, a callback created in an earlier render, and a mutable ref?
function createReactRuntime() { let committedState = 0; function render1() { const count = committedState; const staleCallback = () => count; const updateDirect = () => count + 1; const updateFunctional = (prev) => prev + 1; return { staleCallback, updateDirect, updateFunctional }; } const r1 = render1(); committedState = r1.updateDirect(); committedState = r1.updateDirect(); const countAfterDirect = committedState; committedState = r1.updateFunctional(committedState); committedState = r1.updateFunctional(committedState); const countAfterFunctional = committedState; const staleRead = r1.staleCallback(); const ref = { current: 0 }; ref.current = 3; const refRead = ref.current; return `${countAfterDirect} ${countAfterFunctional} ${staleRead} ${refRead}`; } const result = createReactRuntime(); console.log(result);Why it prints this, traced line by lineShow the output
1 3 0 3
Longer output puzzles
These run past 45 lines, so each opens in its own lesson with the step-by-step trace beside it.
