Skip to content

js_examples

JavaScript is a versatile language primarily known for making web pages interactive. Its capabilities include:

  • Modifying HTML content and structure dynamically.
  • Changing HTML attributes (e.g., an image’s src).
  • Altering CSS styles to change the appearance of elements.
  • Validating user input in forms before submission.
  • Handling user events like clicks, mouse movements, key presses.
  • Making asynchronous requests to servers (AJAX/Fetch API) to load data without reloading the page.
  • Storing data locally in the browser using localStorage or sessionStorage.
  • Creating animations and complex visual effects.
  • And much more, including server-side development (Node.js), mobile apps, and game development.

JavaScript can display data in different ways:

  • window.alert("message"): Shows a simple dialog box. Use sparingly as it blocks user interaction.
  • element.innerHTML = "html content": Writes HTML content into an HTML element. Be cautious with untrusted content due to XSS risks.
  • element.textContent = "text content": Writes plain text into an HTML element. Safer for text-only updates.
  • document.write("content"): Writes directly to the HTML document stream. Strongly discouraged after the page has loaded, as it will overwrite the entire document.
  • console.log("message"): Writes messages to the browser’s developer console. Essential for debugging.

Output methods explained further in relevant sections.

JavaScript code can be placed in HTML documents using the <script> tag:

  • Inside <head>: <script src="path/to/script.js"></script>. Scripts here are fetched and executed before the HTML body is parsed, which can block rendering. Use defer attribute (<script defer src="..."></script>) to ensure the script executes after the HTML is parsed but before DOMContentLoaded. Use async (<script async src="..."></script>) to fetch and execute asynchronously, without blocking parsing, but execution order isn’t guaranteed relative to other async scripts or DOM readiness.
  • Inside <body>: Usually placed at the end, just before </body>. This allows the HTML to parse and render first, so scripts can immediately access DOM elements without waiting. <script src="path/to/script.js"></script>
  • External Files: The recommended approach is to keep JavaScript in separate .js files and link them using <script src="..."></script>. This improves organization, caching, and reusability.

Placement strategies impact page load performance and script behavior.

Key syntax elements include:

  • Literals: Fixed values (e.g., 100, 'Hello', true).
  • Variables: Named storage for data (e.g., let age = 30; const name = 'Alice';).
  • Operators: Perform operations on values (e.g., +, -, *, /, =, ===, &&, ||).
  • Expressions: Combinations of values, variables, and operators that evaluate to a single value (e.g., x * 5).
  • Keywords: Reserved words with special meaning (e.g., let, const, var, function, if, for, return).
  • Statements: Instructions to be executed, typically ending with a semicolon (;), though often optional due to Automatic Semicolon Insertion (ASI).
  • Comments: Ignored by the interpreter, used for explanations (e.g., // single-line, /* multi-line */).
  • Case Sensitivity: JavaScript is case-sensitive (myVariable and myvariable are different).
  • Modern Features: Arrow functions (=>), template literals (`string ${expr}`), destructuring (const {prop} = obj;), spread/rest operators (...).

Syntax details are covered in subsequent sections.

JavaScript programs consist of a sequence of statements.

  • Commands: Each statement is a command for the browser/engine to execute.
  • Semicolons: Statements are typically separated by semicolons (;). While often optional due to ASI, explicit semicolons are a common good practice to avoid ambiguity.
  • White Space: JavaScript ignores multiple spaces and line breaks, allowing for flexible code formatting.
  • Code Blocks: Statements can be grouped into code blocks using curly braces {...}, e.g., in functions or conditional statements. Variables declared with let and const are block-scoped.

Understanding statements is fundamental to writing JavaScript.

Comments are used to add explanatory notes to code, making it more understandable. They are ignored by the JavaScript interpreter.

  • Single-line comments: Start with //. Everything from // to the end of the line is a comment. // This is a single-line comment
  • Multi-line comments: Start with /* and end with */. Can span multiple lines. /* This is a multi-line comment */
  • Use Cases: Explaining complex logic, temporarily disabling code (commenting out).

Well-commented code is easier to maintain.

Variables are containers for storing data values.

  • Declaration: Use let for variables whose values might change, and const for variables whose values should not be reassigned (constants). var is the older way, with function-scope or global-scope, and has hoisting quirks; its use is generally discouraged in modern JavaScript. let age = 25; const name = "Alex";
  • Scope: let and const are block-scoped (visible only within the {...} block they are defined in). var is function-scoped or global-scoped.
  • Assignment: Use the assignment operator = to assign a value to a variable.
  • Naming Rules: Variable names can contain letters, digits, underscores, and dollar signs. They must begin with a letter, $, or _. Case-sensitive.
  • undefined: A variable declared but not assigned a value has the value undefined.
  • Re-declaration: Re-declaring a var variable in the same scope is allowed (but often a bad practice). Re-declaring a let or const variable in the same scope throws an error.

Prefer const by default; use let only when reassignment is necessary.

Arithmetic operators perform mathematical calculations:

  • + (Addition): let sum = 5 + 3; // 8
  • - (Subtraction): let difference = 5 - 3; // 2
  • * (Multiplication): let product = 5 * 3; // 15
  • / (Division): let quotient = 10 / 2; // 5
  • % (Modulus - remainder of division): let remainder = 10 % 3; // 1
  • ** (Exponentiation - ES2016): let power = 2 ** 3; // 8 (2 to the power of 3)
  • ++ (Increment): let count = 5; count++; // count is now 6 (can be pre- or post-increment)
  • -- (Decrement): let val = 5; val--; // val is now 4 (can be pre- or post-decrement)

Operator precedence determines the order of operations (e.g., * and / before + and -). Parentheses () can be used to control the order.

Assignment operators assign values to JavaScript variables.

  • = (Assignment): let x = 10;
  • += (Addition assignment): x += 5; // equivalent to x = x + 5;
  • -= (Subtraction assignment): x -= 3; // equivalent to x = x - 3;
  • *= (Multiplication assignment): x *= 2; // equivalent to x = x * 2;
  • /= (Division assignment): x /= 4; // equivalent to x = x / 4;
  • %= (Modulus assignment): x %= 3; // equivalent to x = x % 3;
  • **= (Exponentiation assignment): x **= 2; // equivalent to x = x ** 2;

These provide shorthand for common operations involving assignment.

Combining strings is called concatenation.

  • + operator: The most common way. let firstName = "John"; let lastName = "Doe"; let fullName = firstName + " " + lastName; // "John Doe"
  • += operator: To append to an existing string. let message = "Hello"; message += " World!"; // "Hello World!"
  • Template Literals (ES6): A more modern and flexible way using backticks (`) and ${expression} placeholders. let city = "New York"; let greeting = Welcome to ${city}!; // "Welcome to New York!" Template literals also support multi-line strings easily.

Template literals are generally preferred for their readability and power.

JavaScript has several data types:

  • Primitive Types:
    • String: Textual data (e.g., 'hello', "world").
    • Number: Numeric values, including integers and floating-point numbers (e.g., 100, 3.14). Also special values like NaN and Infinity.
    • Boolean: Logical values, true or false.
    • undefined: Represents an uninitialized variable or a missing value.
    • null: Represents the intentional absence of any object value. It is an assignment value.
    • Symbol (ES6): Unique and immutable primitive value, often used as object property keys.
    • BigInt (ES2020): For integers larger than the Number type can safely represent.
  • Object Type (Reference Type):
    • Object: A collection of key-value pairs (properties). Includes arrays, functions, dates, etc. JavaScript is dynamically typed, meaning you don’t declare the type of a variable; it’s determined at runtime by the value assigned.

Use the typeof operator to find the type of a variable (e.g., typeof "hello" returns "string").

Objects are collections of properties, where each property is a key-value pair. Keys are usually strings (or Symbols), and values can be any data type, including other objects or functions (methods).

  • Object Literal Syntax: The most common way to create objects. const person = { firstName: "Jane", lastName: "Doe", age: 30, greet: function() { console.log("Hello!"); }, // ES6 method shorthand sayHi() { console.log("Hi!"); } };
  • Accessing Properties:
    • Dot notation: person.firstName
    • Bracket notation: person["lastName"] (useful for dynamic property names or names with special characters).
  • Modifying Properties: person.age = 31;
  • Adding Properties: person.city = "London";
  • Deleting Properties: delete person.age;
  • ES6 Enhancements: Shorthand property names (if key and variable name match), computed property names ({[myVar]: value}), method shorthand.

Objects are fundamental for structuring data in JavaScript.

Functions are blocks of reusable code that perform a specific task. They can take input (parameters) and return output (a value).

  • Function Declaration: function add(a, b) { return a + b; } let sum = add(5, 3); // 8
  • Function Expression: Assigning a function to a variable. const multiply = function(a, b) { return a * b; }; let product = multiply(4, 2); // 8
  • Arrow Functions (ES6): A concise syntax for writing functions. They have different this binding behavior. const subtract = (a, b) => a - b; let difference = subtract(10, 3); // 7 const greet = name => Hello, ${name}!;
  • Parameters and Arguments: Parameters are named in the function definition; arguments are the actual values passed when calling the function.
  • Default Parameters (ES6): function greetUser(name = "Guest") { ... }
  • Rest Parameters (ES6): function sumAll(...numbers) { ... } (gathers remaining arguments into an array).
  • Return Value: Use the return keyword. If omitted, the function returns undefined.

Functions are first-class citizens in JavaScript, meaning they can be treated like any other value (passed as arguments, returned from other functions, assigned to variables).

Events are actions that occur in the browser, such as a user clicking a button, a page finishing loading, or a key being pressed. JavaScript can respond to these events.

  • Event Handlers: Functions that execute when an event occurs.
  • addEventListener() Method: The recommended way to handle events. It allows multiple handlers for a single event and provides more control. const myButton = document.getElementById("myBtn"); myButton.addEventListener("click", function() { console.log("Button clicked!"); });
  • Inline Event Handlers (Older, Less Recommended): <button onclick="myFunction()">Click Me</button>. Harder to maintain and mixes HTML with JavaScript logic.
  • Common Events: click, mouseover, mouseout, keydown, keyup, submit (for forms), load (for window or images).
  • Event Object: Often passed as an argument to the event handler function, containing information about the event (e.g., event.target refers to the element that triggered the event).

Event handling is key to creating interactive web pages.

Strings are sequences of characters. JavaScript provides many built-in methods for working with strings.

  • Creating Strings: Use single quotes ('...'), double quotes ("..."), or template literals (`...`).
  • length Property: "hello".length; // 5
  • Accessing Characters: "hello"[0]; // 'h' (Strings are 0-indexed).
  • Common Methods:
    • indexOf(substring), lastIndexOf(substring): Find position of a substring.
    • slice(start, end), substring(start, end): Extract a portion of a string.
    • replace(old, new), replaceAll(old, new): Replace occurrences of a substring.
    • toUpperCase(), toLowerCase(): Change case.
    • trim(), trimStart(), trimEnd(): Remove whitespace.
    • split(separator): Convert string to an array.
    • includes(substring), startsWith(substring), endsWith(substring): Check for presence of a substring.
    • padStart(targetLength, padString), padEnd(targetLength, padString): Add padding.
  • Immutability: Strings are immutable. String methods return new strings; they don’t modify the original.

Template literals are powerful for embedding expressions within strings: `User: ${userName}`.

JavaScript has a single Number type for both integers and floating-point numbers.

  • Literals: 100, 3.14159, 1.2e6 (exponential notation).
  • Special Values:
    • Infinity, -Infinity: Represent values outside the representable range.
    • NaN (Not-a-Number): Result of invalid math operations (e.g., 0/0, parseInt("apple")).
  • Floating-Point Precision: Be aware of potential inaccuracies with floating-point arithmetic due to binary representation (e.g., 0.1 + 0.2 !== 0.3). For precise calculations (e.g., currency), consider using libraries or strategies like working with integers.
  • Number Object Methods:
    • Number.parseInt(string, radix): Converts a string to an integer.
    • Number.parseFloat(string): Converts a string to a floating-point number.
    • Number.isNaN(value): Checks if a value is NaN (safer than global isNaN()).
    • Number.isFinite(value): Checks if a value is a finite number.
  • Instance Methods (on number values):
    • num.toFixed(digits): Formats a number with a specific number of decimal places, returning a string.
    • num.toPrecision(precision): Formats a number to a specified length, returning a string.
    • num.toString(radix): Converts a number to a string, optionally with a specified base (e.g., 2 for binary, 16 for hexadecimal).

The Math object provides more advanced mathematical functions.

The Math object is a built-in object that has properties and methods for mathematical constants and functions. It’s not a constructor.

  • Constants:
    • Math.PI: The value of Pi (approx. 3.14159).
    • Math.E: Euler’s constant (approx. 2.718).
  • Common Methods:
    • Math.round(x): Rounds to the nearest integer.
    • Math.ceil(x): Rounds up to the nearest integer.
    • Math.floor(x): Rounds down to the nearest integer.
    • Math.trunc(x): Returns the integer part of x (removes decimals).
    • Math.abs(x): Returns the absolute (positive) value.
    • Math.sqrt(x): Returns the square root.
    • Math.pow(base, exponent): Returns base to the power of exponent (same as base ** exponent).
    • Math.min(n1, n2, ...), Math.max(n1, n2, ...): Return the smallest or largest of a set of numbers.
    • Math.random(): Returns a pseudo-random floating-point number between 0 (inclusive) and 1 (exclusive). To get a random integer in a range, combine with Math.floor() and multiplication.

Example: Random integer between 1 and 10: Math.floor(Math.random() * 10) + 1.

The Date object is used to work with dates and times.

  • Creating Dates:
    • new Date(): Current date and time.
    • new Date(milliseconds): Milliseconds since Jan 1, 1970, UTC (Unix Epoch).
    • new Date(dateString): e.g., "2023-10-26", "October 26, 2023 14:30:00".
    • new Date(year, monthIndex, day, hours, minutes, seconds, milliseconds): monthIndex is 0-11.
  • Getting Date/Time Components:
    • getFullYear(), getMonth() (0-11), getDate() (1-31).
    • getHours(), getMinutes(), getSeconds(), getMilliseconds().
    • getDay(): Day of the week (0 for Sunday, 1 for Monday, …, 6 for Saturday).
    • getTime(): Milliseconds since Unix Epoch.
  • Setting Date/Time Components:
    • setFullYear(), setMonth(), setDate(), etc.
  • Formatting:
    • toDateString(): Human-readable date portion.
    • toTimeString(): Human-readable time portion.
    • toLocaleDateString(), toLocaleTimeString(): Locale-specific formatting.
    • toISOString(): ISO 8601 format (e.g., "2023-10-26T14:30:00.000Z"). For complex date manipulations, consider using libraries like date-fns or Day.js, which offer more robust parsing, formatting, and timezone handling.

Example: const today = new Date(); console.log(today.toLocaleDateString());

Arrays are ordered lists of values. Values can be of any data type.

  • Creating Arrays: Use array literals: const fruits = ["Apple", "Banana", "Cherry"];
  • Accessing Elements: 0-indexed: fruits[0]; // "Apple".
  • length Property: fruits.length; // 3.
  • Common Modification Methods (mutate original array):
    • push(item): Adds to end. pop(): Removes from end.
    • unshift(item): Adds to start. shift(): Removes from start.
    • splice(startIndex, deleteCount, ...itemsToAdd): Versatile for adding/removing/replacing elements.
    • sort(compareFunction): Sorts elements. Default is string conversion.
    • reverse(): Reverses element order.
  • Common Access/Iteration Methods (return new array or value, don’t mutate):
    • slice(start, end): Returns a shallow copy of a portion.
    • concat(...arrays): Merges arrays.
    • join(separator): Converts array to string.
    • indexOf(item), lastIndexOf(item): Find item index.
    • includes(item): Checks if an item exists.
    • Iteration Methods (ES5+):
      • forEach(callback): Executes a function for each element.
      • map(callback): Creates a new array by transforming each element.
      • filter(callback): Creates a new array with elements that pass a test.
      • reduce(callback, initialValue): Reduces array to a single value.
      • find(callback): Returns the first element that passes a test.
      • findIndex(callback): Returns the index of the first element that passes a test.
      • some(callback), every(callback): Test if some/all elements pass a test.
  • Spread Operator (...) (ES6): Useful for copying ([...oldArray]), merging, and passing elements as arguments.
  • Destructuring Assignment (ES6): const [first, second] = fruits;

Arrays are a cornerstone of data manipulation in JavaScript.

JavaScript often performs automatic type conversion (coercion) when operators are used with different types. It’s important to understand this, but explicit conversion is usually clearer.

  • Explicit Conversion:
    • To String: String(123) or 123.toString().
    • To Number: Number("456"), parseInt("100px") (parses until non-digit), parseFloat("3.14em"). The unary plus operator can also convert to number: +"789".
    • To Boolean: Boolean(value). Falsy values (false, 0, "", null, undefined, NaN) convert to false; all others (truthy) convert to true.
  • Implicit Coercion Examples:
    • "5" + 3 results in "53" (number converted to string for concatenation).
    • "10" - 5 results in 5 (string converted to number for subtraction).
    • if (value) {...}: value is implicitly converted to boolean.
  • Checking Type: typeof value.
  • Checking if Array: Array.isArray(value).
  • Checking if Date: value instanceof Date.

Understanding coercion helps debug unexpected behavior. Prefer strict equality (===) to avoid unwanted type coercion during comparisons.

JavaScript Booleans and Truthy/Falsy Values

Section titled “JavaScript Booleans and Truthy/Falsy Values”

Booleans represent logical values: true or false.

  • Boolean Literals: true, false.
  • Comparisons Yield Booleans: 5 > 3; // true
  • Truthy and Falsy Values: In contexts where a boolean is expected (like an if condition), JavaScript coerces other types to boolean.
    • Falsy Values: These convert to false:
      • false
      • 0 (and -0)
      • "" (empty string)
      • null
      • undefined
      • NaN (Not-a-Number)
    • Truthy Values: All other values are truthy, including:
      • Non-empty strings (e.g., "hello", "0", "false")
      • Non-zero numbers (e.g., 1, -1)
      • Objects (including empty objects {} and empty arrays [])
      • Functions
  • Boolean() Function: Explicitly converts a value to a boolean: Boolean("text"); // true, Boolean(0); // false.

Understanding truthy/falsy is crucial for conditional logic.

Comparison operators compare two values and return a boolean (true or false).

  • Equality:
    • == (Loose/Abstract Equality): Compares values after performing type coercion if types are different. Generally discouraged due to unpredictable behavior. 5 == "5"; // true
    • === (Strict Equality): Compares values without type coercion. If types are different, returns false. Preferred for most comparisons. 5 === "5"; // false 5 === 5; // true
  • Inequality:
    • != (Loose Inequality): 5 != "5"; // false
    • !== (Strict Inequality): 5 !== "5"; // true Preferred.
  • Relational Operators:
    • > (Greater than): 10 > 5; // true
    • < (Less than): 10 < 5; // false
    • >= (Greater than or equal to): 10 >= 10; // true
    • <= (Less than or equal to): 5 <= 10; // true When comparing objects (including arrays and functions), equality operators (==, ===) check if they refer to the same object in memory, not if their contents are identical.

Always prefer strict comparison (===, !==) to avoid subtle bugs from type coercion.

Conditional statements execute different blocks of code based on conditions.

  • if statement: Executes code if a condition is true. if (age >= 18) { console.log("Adult"); }
  • if...else statement: Executes one block if true, another if false. if (score >= 50) { console.log("Pass"); } else { console.log("Fail"); }
  • if...else if...else statement: For multiple conditions. if (grade >= 90) { console.log("A"); } else if (grade >= 80) { console.log("B"); } else { console.log("C or below"); }
  • switch statement: Selects one of many code blocks to execute. Useful for multiple discrete values. switch (dayOfWeek) { case "Monday": console.log("Start of week"); break; case "Friday": console.log("Almost weekend!"); break; default: console.log("Another day"); } (Requires break to prevent fall-through).
  • Ternary Operator (condition ? exprIfTrue : exprIfFalse): A concise way to write simple if-else statements. let type = age >= 18 ? "Adult" : "Minor";

Conditionals are fundamental for controlling program flow.

Loops repeat a block of code multiple times.

  • for loop: When you know the number of iterations. for (let i = 0; i < 5; i++) { console.log(i); } // 0, 1, 2, 3, 4
  • while loop: Repeats as long as a condition is true. Condition checked before each iteration. let count = 0; while (count < 3) { console.log(count); count++; } // 0, 1, 2
  • do...while loop: Similar to while, but the code block executes at least once before the condition is checked. let num = 0; do { console.log(num); num++; } while (num < 0); // 0
  • for...in loop: Iterates over the enumerable properties of an object (usually keys). const person = { name: "Alice", age: 30 }; for (const key in person) { console.log(${key}: ${person[key]}); }
  • for...of loop (ES6): Iterates over the values of iterable objects (like Arrays, Strings, Maps, Sets). const colors = ["red", "green", "blue"]; for (const color of colors) { console.log(color); }
  • break statement: Exits a loop prematurely.
  • continue statement: Skips the current iteration and proceeds to the next.

Choose the loop type that best fits the iteration logic. for...of is generally preferred for iterating over array values.

JavaScript Error Handling (try...catch...finally)

Section titled “JavaScript Error Handling (try...catch...finally)”

Error handling allows you to gracefully manage runtime errors.

  • try block: Contains code that might throw an error.

  • catch block: Executes if an error occurs in the try block. It receives an error object with details (e.g., error.message, error.name).

  • finally block: Executes after try (and catch, if an error occurred), regardless of whether an error was thrown. Useful for cleanup tasks (e.g., closing resources).

  • throw statement: Creates custom errors. throw new Error("Something went wrong!"); or throw "Custom error message";

    try { let result = riskyOperation(); console.log(result); } catch (error) { console.error("An error occurred:", error.message); } finally { console.log("Operation finished, cleanup if needed."); }

  • Error Objects: Built-in error types include Error, SyntaxError, ReferenceError, TypeError, etc. You can create custom error classes by extending Error.

Proper error handling makes applications more robust.

Regular expressions are patterns used to match character combinations in strings. They are powerful for text searching, validation, and manipulation.

  • Creating RegExp:
    • Literal: const pattern = /abc/i; (i is a flag for case-insensitivity).
    • Constructor: const pattern = new RegExp("abc", "i");
  • Common RegExp Methods (on Strings):
    • string.match(pattern): Returns an array of matches or null.
    • string.search(pattern): Returns the index of the first match or -1.
    • string.replace(pattern, replacement): Replaces matches with a string or function result.
    • string.split(pattern): Splits the string by matches.
  • RegExp Methods (on RegExp object):
    • pattern.test(string): Returns true if there’s a match, false otherwise.
    • pattern.exec(string): Returns an array of match details or null; advances position for global searches.
  • Common Pattern Syntax:
    • . (any character except newline), \d (digit), \w (word char), \s (whitespace).
    • * (0 or more), + (1 or more), ? (0 or 1).
    • [] (character set), () (capturing group), | (OR).
    • ^ (start of string/line), $ (end of string/line).
  • Flags: g (global), i (case-insensitive), m (multiline).

Example: Validate email format (simplified): const emailPattern = /^\S+@\S+\.\S+$/; console.log(emailPattern.test("test@example.com")); // true

JavaScript Objects (Revisited and Advanced)

Section titled “JavaScript Objects (Revisited and Advanced)”

Objects are fundamental in JavaScript, serving as collections of key-value pairs.

  • Object Literals: const car = { make: "Toyota", model: "Camry" };
  • Constructors: Using new with a constructor function (e.g., new Date(), or custom constructors). function Person(name, age) { this.name = name; this.age = age; } const person1 = new Person("Bob", 40);
  • Prototypes and Inheritance: Objects inherit properties and methods from their prototype. This forms the basis of JavaScript’s prototypal inheritance.
  • this Keyword: Its value depends on how a function is called (e.g., in an object method, this refers to the object; in arrow functions, this is lexically bound).
  • ES6+ Features:
    • Class syntax: Syntactic sugar over prototypal inheritance (class Car { constructor(...) { ... } drive() { ... } }).
    • Modules: For organizing code into reusable pieces (import/export).
    • Getters and Setters: get propertyName() { ... }, set propertyName(value) { ... }.
    • Object.keys(obj), Object.values(obj), Object.entries(obj): To get an array of keys, values, or [key, value] pairs.
    • Object.assign(target, ...sources): To copy properties from source objects to a target object.
    • Spread syntax for objects (...): For cloning or merging objects (const newObj = { ...oldObj, newProp: val };).

Objects are mutable (their properties can be changed after creation), unlike primitive types.

Properties are the key-value pairs that make up an object.

  • Accessing:
    • Dot notation: object.propertyName
    • Bracket notation: object["propertyName"] or object[variableContainingPropertyName]
  • Adding/Modifying: object.newProperty = "value"; or object.existingProperty = "newValue";
  • Deleting: delete object.propertyName; (Removes the property from the object).
  • Enumerating Properties:
    • for...in loop: Iterates over enumerable, own and inherited properties (use obj.hasOwnProperty(key) to check for own properties).
    • Object.keys(obj): Returns an array of own enumerable property names.
    • Object.getOwnPropertyNames(obj): Returns an array of all own property names (enumerable or not).
  • Property Descriptors: Properties have internal attributes (descriptors) like value, writable, enumerable, configurable. These can be controlled using Object.defineProperty() and Object.defineProperties().
  • Shorthand Properties (ES6): If a variable name is the same as the desired property key: const name = "Alice"; const person = { name, age: 30 }; // person.name is "Alice"
  • Computed Property Names (ES6): Use an expression in brackets for the key: const propName = "dynamicKey"; const obj = { [propName]: "some value" };

Understanding how to work with object properties is essential for effective JavaScript programming.