# Lesson 00: Getting Started & Assessment Review **Duration:** 45 minutes **Objective:** Understand JavaScript fundamentals and identify key areas for focused study --- ## Introduction Welcome to your JavaScript interview preparation curriculum! This lesson reviews the diagnostic assessment and establishes foundational knowledge that will be built upon in subsequent lessons. Based on common evaluation results, most developers need focused review in: - Type coercion and equality - Closures and scope - The `this` keyword and context binding - Prototypes and inheritance - Modern ES6+ syntax - Asynchronous execution patterns --- ## Part 1: JavaScript Type System Fundamentals ### 1.1 Primitive Types JavaScript has 7 primitive types: ```javascript typeof undefined; // "undefined" typeof true; // "boolean" typeof 42; // "number" typeof 9007199254740991n; // "bigint" typeof "hello"; // "string" typeof Symbol(); // "symbol" typeof null; // "object" ⚠️ This is a bug in JavaScript! ``` **The `null` Bug:** `typeof null` returning `"object"` is a historical bug that can't be fixed without breaking existing code. `null` represents the intentional absence of any object value. ```javascript // Checking for null correctly const value = null; console.log(value === null); // true console.log(typeof value === "object" && value === null); // true ``` ### 1.2 Reference Types Objects, Arrays, and Functions are reference types: ```javascript typeof {}; // "object" typeof []; // "object" (arrays are objects) typeof function(){}; // "function" ``` **Key Difference:** - **Primitives** are compared by value - **References** are compared by reference (memory location) ```javascript // Primitives - value comparison const a = 42; const b = 42; console.log(a === b); // true // References - memory location comparison const arr1 = [1, 2, 3]; const arr2 = [1, 2, 3]; console.log(arr1 === arr2); // false (different objects in memory) console.log(arr1 === arr1); // true (same reference) const arr3 = arr1; console.log(arr3 === arr1); // true (same reference) ``` --- ## Part 2: Floating-Point Precision ### 2.1 The 0.1 + 0.2 Problem JavaScript uses IEEE 754 double-precision floating-point format. Some decimal numbers cannot be represented exactly in binary. ```javascript console.log(0.1 + 0.2); // 0.30000000000000004 console.log(0.1 + 0.2 === 0.3); // false ⚠️ ``` **Why?** - 0.1 in binary: `0.0001100110011...` (repeating) - Computer must round, introducing tiny errors - These errors accumulate during operations **Solutions:** ```javascript // 1. Use epsilon comparison function areClose(a, b, epsilon = 0.0001) { return Math.abs(a - b) < epsilon; } console.log(areClose(0.1 + 0.2, 0.3)); // true // 2. Use Number.EPSILON console.log(Math.abs(0.1 + 0.2 - 0.3) < Number.EPSILON); // true // 3. Work with integers (convert to cents, etc.) const price1 = 10; // 10 cents const price2 = 20; // 20 cents const total = price1 + price2; // 30 cents (exact) // 4. Round to fixed decimals const result = Math.round((0.1 + 0.2) * 100) / 100; // 0.3 ``` **Interview Tip:** Always mention this caveat when working with money or precise calculations. Suggest using integers or decimal libraries. --- ## Part 3: Var, Let, and Const ### 3.1 The Problem with `var` ```javascript // Function scope (not block scope) function example() { if (true) { var x = 5; } console.log(x); // 5 (var leaks out of the block!) } // Hoisting console.log(y); // undefined (not an error!) var y = 10; // What actually happens: var y; console.log(y); // undefined y = 10; ``` **The Classic Loop Problem:** ```javascript for (var i = 0; i < 3; i++) { setTimeout(() => console.log(i), 100); } // Logs: 3, 3, 3 // Why? All callbacks share the same 'i' variable // By the time they execute, the loop finished and i = 3 ``` ### 3.2 Let and Const (ES6+) ```javascript // Block scope if (true) { let x = 5; const y = 10; } console.log(x); // ReferenceError console.log(y); // ReferenceError // No hoisting issues console.log(z); // ReferenceError (temporal dead zone) let z = 15; // Loop with let creates a new binding per iteration for (let i = 0; i < 3; i++) { setTimeout(() => console.log(i), 100); } // Logs: 0, 1, 2 ✅ ``` **Const Rules:** ```javascript const x = 10; x = 20; // TypeError: Assignment to constant variable // But objects are mutable! const obj = { name: "Alice" }; obj.name = "Bob"; // ✅ Allowed (modifying property) obj = {}; // ❌ TypeError (reassigning variable) // Use Object.freeze() for immutability const frozen = Object.freeze({ name: "Alice" }); frozen.name = "Bob"; // Silently fails (throws in strict mode) console.log(frozen.name); // "Alice" ``` **Best Practice:** Use `const` by default, `let` when you need reassignment, avoid `var`. --- ## Part 4: Array Behavior and Holes ### 4.1 Sparse Arrays ```javascript const arr = [1, 2, 3]; arr[10] = 11; console.log(arr.length); // 11 (not 4!) console.log(arr); // [1, 2, 3, empty × 7, 11] console.log(arr[5]); // undefined (hole in array) ``` **Array Length:** - Length is always the highest index + 1 - Creating holes doesn't initialize elements ```javascript const sparse = new Array(5); console.log(sparse.length); // 5 console.log(sparse[0]); // undefined console.log(0 in sparse); // false (hole, not undefined value) const filled = [undefined, undefined]; console.log(0 in filled); // true (actual undefined value) ``` **Array Methods and Holes:** ```javascript const arr = [1, , 3]; // Array with hole arr.forEach(x => console.log(x)); // 1, 3 (skips holes) arr.map(x => x * 2); // [2, empty, 6] (preserves holes) Array.from(arr); // [1, undefined, 3] (converts holes) ``` --- ## Part 5: Type Coercion Essentials ### 5.1 Truthy and Falsy Values **Falsy values** (8 total): ```javascript if (false) {} // false if (0) {} // 0 if (-0) {} // -0 if (0n) {} // 0n (BigInt zero) if ("") {} // empty string if (null) {} // null if (undefined) {} // undefined if (NaN) {} // NaN ``` Everything else is **truthy**, including: ```javascript if ("0") {} // truthy (non-empty string) if ("false") {} // truthy if ([]) {} // truthy (empty array) if ({}) {} // truthy (empty object) if (function(){}) {} // truthy ``` ### 5.2 Unary Plus Operator ```javascript console.log(+"42"); // 42 console.log(+"3.14"); // 3.14 console.log(+"hello"); // NaN console.log(+true); // 1 console.log(+false); // 0 console.log(+null); // 0 console.log(+undefined); // NaN // Quick number conversion const input = "123"; const num = +input; // Same as Number(input) ``` ### 5.3 Addition Coercion ```javascript // String concatenation wins console.log("" + 1 + 2); // "12" (1 converts to string first) console.log(1 + 2 + ""); // "3" (addition happens first) console.log("" + []); // "" (array becomes empty string) console.log("" + {}); // "[object Object]" // Arrays console.log([] + []); // "" (both arrays convert to empty strings) console.log([1] + [2]); // "12" console.log([1, 2] + [3]); // "1,23" ``` --- ## Part 6: Essential Function Concepts ### 6.1 Function Declarations vs Expressions ```javascript // Declaration - hoisted foo(); // ✅ Works function foo() { console.log("I'm hoisted!"); } // Expression - not hoisted bar(); // ❌ ReferenceError const bar = function() { console.log("I'm not hoisted!"); }; ``` ### 6.2 Arrow Functions Preview Arrow functions have important differences (covered in Lesson 02): ```javascript // No 'this' binding const obj = { value: 42, regularFunc: function() { console.log(this.value); // 42 }, arrowFunc: () => { console.log(this.value); // undefined (or global value) } }; obj.regularFunc(); // 42 obj.arrowFunc(); // undefined ``` **Key Differences:** - Arrow functions inherit `this` from outer scope - Cannot be used as constructors - No `arguments` object - Cannot use `yield` (not generators) --- ## Part 7: Common Interview Gotchas ### 7.1 Object Property Duplicates ```javascript const obj = { a: 1, b: 2, a: 3 }; console.log(obj.a); // 3 (last value wins) ``` In modern JavaScript, duplicate keys are allowed. The last value overwrites previous ones. ### 7.2 Automatic Semicolon Insertion (ASI) ```javascript // This looks fine... function getData() { return { name: "Alice" } } console.log(getData()); // undefined ⚠️ // JavaScript interprets it as: function getData() { return; // semicolon inserted! { name: "Alice" } } // Fix: Keep opening brace on same line function getData() { return { name: "Alice" }; } ``` ### 7.3 Implicit Global Variables ```javascript function oops() { x = 10; // ⚠️ Creates global variable (no var/let/const) } oops(); console.log(x); // 10 (global!) // Even worse: let x = y = 10; // This is really: let x = (y = 10) // x is local, y is global! function example() { let x = y = 20; } example(); console.log(y); // 20 (global!) ``` **Fix:** Always use `"use strict";` and declare all variables. ```javascript "use strict"; function safe() { x = 10; // ReferenceError: x is not defined } ``` --- ## Part 8: Preparing for Deep Dive Topics ### Topics Covered in Upcoming Lessons **Lesson 01 - Type System & Coercion:** - Double equals vs triple equals - Type conversion rules - Advanced coercion scenarios **Lesson 02 - This Binding:** - How `this` is determined - Call, apply, and bind - Arrow functions and `this` **Lesson 03 - Closures:** - Lexical scope - Practical closure patterns - Memory implications **Lesson 04 - Event Loop:** - Call stack, task queue, microtask queue - Understanding async execution order **Lesson 05 - Promises:** - Promise states and chaining - Error handling - Async/await patterns **Lesson 06 - Prototypes:** - Prototype chain - Constructor functions vs classes - Inheritance patterns **Lesson 07 - ES6+ Features:** - Destructuring - Spread/rest operators - Template literals, default parameters **Lesson 08 - Array Methods:** - Map, filter, reduce - ForEach vs for loops - Functional programming concepts --- ## Key Takeaways ✅ **Remember:** 1. `typeof null` returns `"object"` (historical bug) 2. Never use `===` with floating-point decimals 3. `var` is function-scoped, `let`/`const` are block-scoped 4. Arrays are compared by reference, not value 5. Use `const` by default, `let` when needed, avoid `var` 6. Arrow functions don't have their own `this` binding 7. Array length = highest index + 1 8. Always declare variables to avoid implicit globals --- ## Practice Tips 1. **Run code examples** - Don't just read them 2. **Predict output** before running code 3. **Understand "why"** - Memorization isn't enough 4. **Practice explaining** concepts out loud 5. **Focus on weak areas** identified in your evaluation --- ## Next Steps Complete the medium-difficulty quiz to test your understanding of these fundamentals. Then proceed to Lesson 01 to dive deeper into the type system. **Time to complete quiz:** 10-15 minutes