JavaScript Variables & Data Types Master Guide

Understanding JavaScript Variables

Variables in JavaScript are fundamental containers that store data values. They act as named storage locations that can hold different types of information and can be referenced throughout your code. JavaScript variables are dynamically typed, meaning you don't need to specify the data type when declaring them - the type is determined automatically based on the value assigned.

Key Characteristics of JavaScript Variables

  • Dynamic Typing - Variables can hold any data type and can change types during execution
  • Case Sensitive - Variable names are case-sensitive (myVar ≠ myvar)
  • Loosely Typed - No strict type enforcement - flexibility with automatic type conversion

Variable Declaration in JavaScript

JavaScript provides three ways to declare variables: var, let, and const. Each has different scoping rules and use cases. Understanding when to use each declaration method is crucial for writing clean, maintainable JavaScript code.

javascript
1// VAR - Function scoped (older method)
2var firstName = "John";
3var age = 30;
4var isActive = true;
5
6// LET - Block scoped (modern replacement for var)
7let lastName = "Doe";
8let score = 95.5;
9let isOnline = false;
10
11// CONST - Block scoped, cannot be reassigned
12const PI = 3.14159;
13const API_KEY = "abc123def456";
14const MAX_USERS = 1000;
15
16// Reassignment examples
17let counter = 0;
18counter = 1;                    // Valid - let allows reassignment
19
20const TAX_RATE = 0.07;
21// TAX_RATE = 0.08;             // Error - const prevents reassignment
22
23// Multiple declarations
24let x = 1, y = 2, z = 3;
25const DEFAULT_COLOR = "blue", FALLBACK_COLOR = "red";
26
27// Declaration without initialization
28let uninitializedVar;           // Value is undefined
29var oldStyleVar;                // Also undefined
30// const mustInitialize;        // Error - const requires initialization

Declaration Methods Comparison

  • var - Function-scoped, hoisted, can be redeclared - avoid in modern code
  • let - Block-scoped, hoisted but not initialized, cannot be redeclared in same scope
  • const - Block-scoped, cannot be reassigned, must be initialized - use by default

JavaScript Naming Conventions & Rules

Proper variable naming is essential for code readability and maintainability. JavaScript has specific rules for variable names and established conventions that developers should follow.

javascript
1// Valid variable names
2let userName = "Alice";
3let _privateVar = "internal";
4let $element = document.getElementById('main');
5let user2 = "secondary";
6let camelCaseVariable = "standard";
7let CONSTANT_VALUE = "screaming snake case";
8
9// Invalid variable names (will cause errors)
10// let 2ndUser = "invalid";          // Cannot start with number
11// let user-name = "invalid";        // Hyphens not allowed
12// let let = "invalid";              // Reserved keyword
13// let user name = "invalid";        // Spaces not allowed
14
15// Good naming practices
16const MAX_RETRY_ATTEMPTS = 3;
17let isLoading = false;
18let itemPrice = 19.99;
19let hasUserPermission = true;
20let apiEndpoint = "/api/users";
21
22// Poor naming practices (avoid)
23let a = "Alice";                    // Too vague
24let x1 = 42;                        // Non-descriptive
25let flag = true;                    // Unclear purpose
26let temp = "temporary";             // Temporary names that persist
27
28// Descriptive vs non-descriptive
29let elapsedTimeInSeconds = 3600;    // Good - clear purpose
30let et = 3600;                      // Bad - ambiguous
31
32let isDataValid = true;             // Good - boolean clarity
33let dataCheck = true;               // Bad - unclear type

Naming Rules & Best Practices

  • Must Start With - Letter (a-z, A-Z), underscore (_), or dollar sign ($)
  • Can Contain - Letters, numbers, underscores, dollar signs
  • Case Sensitivity - myVariable ≠ myvariable ≠ MyVariable
  • Reserved Words - Avoid let, const, function, class, etc.
  • Camel Case - Use for variables and functions (firstName, calculateTotal)
  • UPPER_CASE - Use for constants (MAX_SIZE, API_URL)

JavaScript Primitive Data Types

JavaScript has 7 primitive data types that represent single values. Primitives are immutable - when you change them, you create new values rather than modifying the existing ones.

javascript
1// 1. Number - integer and floating point
2let integer = 42;
3let float = 3.14159;
4let scientific = 2.5e-4;        // 0.00025
5let hex = 0xFF;                 // 255 in hexadecimal
6let infinity = Infinity;
7let notANumber = NaN;
8
9// 2. String - text data
10let singleQuote = 'Hello';
11let doubleQuote = "World";
12let backtick = `Template Literal`;
13let escaped = "Line 1\nLine 2"; // New line
14let unicode = "Hello \u{1F44B}"; // Unicode emoji
15
16// 3. Boolean - true/false
17let isActive = true;
18let isEmpty = false;
19let isGreater = 5 > 3;          // true
20
21// 4. Undefined - declared but not assigned
22let undefinedVar;
23console.log(undefinedVar);       // undefined
24
25// 5. Null - intentional absence of value
26let emptyValue = null;
27
28// 6. Symbol - unique and immutable
29let sym1 = Symbol('description');
30let sym2 = Symbol('description');
31console.log(sym1 === sym2);     // false - each Symbol is unique
32
33// 7. BigInt - large integers beyond Number limit
34let bigNumber = 9007199254740991n;
35let huge = 1234567890123456789012345678901234567890n;
36
37// Type checking with typeof
38console.log(typeof 42);          // "number"
39console.log(typeof "hello");     // "string"
40console.log(typeof true);        // "boolean"
41console.log(typeof undefined);   // "undefined"
42console.log(typeof null);        // "object" (historical quirk)
43console.log(typeof Symbol());    // "symbol"
44console.log(typeof 123n);        // "bigint"

Number Data Type in Depth

JavaScript uses a single Number type for both integers and floating-point numbers. All numbers are stored as 64-bit floating-point values following the IEEE 754 standard.

javascript
1// Number representations
2let decimal = 42;
3let floating = 3.14159;
4let negative = -15.5;
5let scientific = 1.23e6;        // 1,230,000
6let hex = 0x2A;                 // 42 in hexadecimal
7let octal = 0o52;               // 42 in octal
8let binary = 0b101010;          // 42 in binary
9
10// Special numeric values
11let infinity = Infinity;
12let negativeInfinity = -Infinity;
13let notANumber = NaN;
14
15// Number precision issues (IEEE 754 limitation)
16console.log(0.1 + 0.2);         // 0.30000000000000004
17console.log(0.1 + 0.2 === 0.3); // false
18
19// Number methods and properties
20let num = 123.456;
21console.log(num.toFixed(2));    // "123.46"
22console.log(num.toPrecision(5)); // "123.46"
23console.log(num.toString(16));  // "7b.74bc6a7ef9dc" in hex
24
25// Number object properties
26console.log(Number.MAX_VALUE);   // 1.7976931348623157e+308
27console.log(Number.MIN_VALUE);   // 5e-324
28console.log(Number.MAX_SAFE_INTEGER); // 9007199254740991
29console.log(Number.MIN_SAFE_INTEGER); // -9007199254740991
30
31// Checking number types
32console.log(Number.isInteger(42));    // true
33console.log(Number.isInteger(42.5));  // false
34console.log(Number.isSafeInteger(9007199254740991)); // true
35console.log(Number.isNaN(NaN));       // true
36console.log(isNaN("hello"));          // true (global isNaN)
37
38// Arithmetic operations
39let a = 10, b = 3;
40console.log(a + b);   // 13
41console.log(a - b);   // 7
42console.log(a * b);   // 30
43console.log(a / b);   // 3.333...
44console.log(a % b);   // 1 (remainder)
45console.log(a ** b);  // 1000 (exponentiation)
46
47// Increment/decrement
48let count = 5;
49count++;              // 6 (post-increment)
50++count;              // 7 (pre-increment)
51count--;              // 6 (post-decrement)

String Data Type Comprehensive Guide

Strings in JavaScript represent textual data and are immutable sequences of UTF-16 code units. They can be created using single quotes, double quotes, or template literals.

javascript
1// String creation methods
2let single = 'Single quoted string';
3let double = "Double quoted string";
4let backticks = `Template literal string`;
5
6// Template literals (ES6+)
7let name = "Alice";
8let age = 25;
9let greeting = `Hello, ${name}! You are ${age} years old.`;
10// "Hello, Alice! You are 25 years old."
11
12// Multi-line strings
13let multiLine = `This is
14a multi-line
15string using
16template literals`;
17
18// Escape sequences
19let newLine = "Line 1\nLine 2";
20let tab = "Column1\tColumn2";
21let quote = "He said, \"Hello!\"";
22let backslash = "Path: C:\\Program Files\\";
23let unicode = "Smiley: \u{1F600}";
24
25// String properties and methods
26let text = "JavaScript Programming";
27
28// Properties
29console.log(text.length);        // 22
30
31// Access methods
32console.log(text[0]);            // "J"
33console.log(text.charAt(4));     // "S"
34console.log(text.charCodeAt(0)); // 74 (Unicode of 'J')
35
36// Case methods
37console.log(text.toUpperCase()); // "JAVASCRIPT PROGRAMMING"
38console.log(text.toLowerCase()); // "javascript programming"
39
40// Search methods
41console.log(text.indexOf("Script"));    // 4
42console.log(text.lastIndexOf("a"));     // 3
43console.log(text.includes("Java"));     // true
44console.log(text.startsWith("Java"));   // true
45console.log(text.endsWith("ing"));      // true
46
47// Extract methods
48console.log(text.slice(0, 10));         // "JavaScript"
49console.log(text.substring(0, 10));     // "JavaScript"
50console.log(text.substr(4, 6));         // "Script"
51
52// Modification methods
53console.log(text.replace("Java", "Type")); // "TypeScript Programming"
54console.log("  hello  ".trim());           // "hello"
55console.log("hello".padStart(8, "*"));     // "***hello"
56console.log("hello".padEnd(8, "*"));       // "hello***"
57
58// Split and join
59let tags = "js,html,css";
60console.log(tags.split(","));            // ["js", "html", "css"]
61console.log(["js", "html", "css"].join(" | ")); // "js | html | css"

Boolean and Logical Operations

Boolean values represent true or false and are fundamental for controlling program flow through conditional statements and logical operations.

javascript
1// Boolean values
2let isActive = true;
3let isEmpty = false;
4let hasPermission = true;
5
6// Boolean creation from other types
7let fromString = Boolean("hello");     // true
8let fromEmptyString = Boolean("");     // false
9let fromNumber = Boolean(42);          // true
10let fromZero = Boolean(0);             // false
11let fromObject = Boolean({});          // true
12let fromNull = Boolean(null);          // false
13let fromUndefined = Boolean(undefined); // false
14
15// Comparison operators (return booleans)
16let equal = (5 == 5);           // true
17let strictEqual = (5 === '5');  // false
18let notEqual = (5 != 3);        // true
19let strictNotEqual = (5 !== '5'); // true
20let greaterThan = (10 > 5);     // true
21let lessThan = (10 < 5);        // false
22let greaterOrEqual = (10 >= 10); // true
23let lessOrEqual = (10 <= 5);    // false
24
25// Logical operators
26let andResult = (true && false);    // false
27let orResult = (true || false);     // true
28let notResult = (!true);            // false
29
30// Short-circuit evaluation
31let user = { name: "John" };
32let displayName = user && user.name;  // "John"
33let defaultName = user.name || "Guest"; // "John"
34
35// Truthy and falsy values
36// Falsy: false, 0, "", null, undefined, NaN
37// Truthy: everything else
38
39// Practical examples
40let age = 25;
41let hasLicense = true;
42let canDrive = (age >= 18 && hasLicense); // true
43
44let score = 85;
45let isPassing = (score >= 60);           // true
46let isExcellent = (score >= 90);         // false
47
48// Ternary operator
49let status = (score >= 60) ? "Pass" : "Fail";
50let message = (age >= 21) ? "Adult" : "Minor";
51
52// Nullish coalescing operator (ES2020)
53let userName = null;
54let displayUser = userName ?? "Anonymous"; // "Anonymous"
55
56let count = 0;
57let displayCount = count ?? "Not set";     // 0 (not falsy)
58
59// Optional chaining (ES2020)
60let userProfile = {
61    personal: {
62        name: "Alice",
63        age: 30
64    }
65};
66let city = userProfile?.personal?.address?.city; // undefined (no error)

Special Primitive Types: undefined, null, Symbol, BigInt

JavaScript includes special primitive types that serve specific purposes in the language, from representing absence of values to handling large numbers and creating unique identifiers.

javascript
1// Undefined - variable declared but not assigned
2let undefinedVar;
3console.log(undefinedVar);           // undefined
4console.log(typeof undefinedVar);    // "undefined"
5
6// Functions without return statement
7function noReturn() {
8    // no return
9}
10console.log(noReturn());             // undefined
11
12// Null - intentional absence of any object value
13let emptyValue = null;
14console.log(emptyValue);             // null
15console.log(typeof emptyValue);      // "object" (historical JavaScript quirk)
16
17// Symbol - unique and immutable primitive
18let sym1 = Symbol("id");
19let sym2 = Symbol("id");
20console.log(sym1 === sym2);          // false - each Symbol is unique
21
22// Symbol usage for object properties
23let user = {
24    name: "John",
25    [Symbol("id")]: 123,            // Hidden property
26    [Symbol.for("email")]: "john@example.com" // Global symbol
27};
28
29// Well-known symbols
30let arr = [1, 2, 3];
31arr[Symbol.iterator];                // Built-in iterator symbol
32
33// BigInt - integers beyond Number limits
34let big1 = 9007199254740991n;       // n suffix
35let big2 = BigInt("123456789012345678901234567890");
36
37// BigInt operations
38console.log(big1 + 1n);              // 9007199254740992n
39console.log(big1 * 2n);              // 18014398509481982n
40// console.log(big1 + 1);            // Error: cannot mix BigInt and Number
41
42// BigInt comparisons work with numbers
43console.log(1n === 1);               // false (different types)
44console.log(1n == 1);                // true (value equality)
45console.log(1n < 2);                 // true
46
47// Type detection and conversion
48console.log(typeof undefined);       // "undefined"
49console.log(typeof null);            // "object"
50console.log(typeof Symbol());        // "symbol"
51console.log(typeof 123n);            // "bigint"
52
53// Checking for null/undefined
54let value = null;
55console.log(value === null);         // true
56console.log(value === undefined);    // false
57console.log(value == null);          // true (checks both null and undefined)

Type Conversion and Coercion in JavaScript

JavaScript performs automatic type conversion (coercion) and allows explicit type conversion. Understanding how and when types are converted is crucial for avoiding unexpected behavior.

javascript
1// Explicit type conversion
2let stringToNumber = Number("42");        // 42
3let numberToString = String(42);          // "42"
4let boolToString = String(true);          // "true"
5let stringToBool = Boolean("hello");      // true
6
7// Parse methods for strings
8let intParse = parseInt("42px");          // 42
9let floatParse = parseFloat("3.14cm");    // 3.14
10let intBase = parseInt("1010", 2);       // 10 (binary to decimal)
11
12// Implicit type coercion (automatic)
13let coerced1 = "5" + 2;                   // "52" (string concatenation)
14let coerced2 = "5" - 2;                   // 3 (numeric subtraction)
15let coerced3 = "5" * "2";                 // 10 (numeric multiplication)
16let coerced4 = !!"hello";                // true (boolean conversion)
17
18// Common conversion patterns
19// To Number
20let num1 = +"123";                       // 123 (unary plus)
21let num2 = +true;                         // 1
22let num3 = +false;                        // 0
23let num4 = +null;                         // 0
24let num5 = +undefined;                    // NaN
25let num6 = +"";                          // 0
26
27// To String
28let str1 = 123 + "";                      // "123"
29let str2 = true + "";                     // "true"
30let str3 = null + "";                     // "null"
31let str4 = undefined + "";                // "undefined"
32
33// To Boolean
34let bool1 = !!0;                          // false
35let bool2 = !!1;                          // true
36let bool3 = !!"";                         // false
37let bool4 = !!"text";                     // true
38let bool5 = !!null;                       // false
39let bool6 = !!undefined;                  // false
40let bool7 = !!{};                         // true
41
42// Loose equality (==) with type coercion
43console.log(5 == "5");                    // true
44console.log(true == 1);                   // true
45console.log(false == 0);                  // true
46console.log(null == undefined);           // true
47console.log("" == 0);                     // true
48
49// Strict equality (===) without coercion
50console.log(5 === "5");                   // false
51console.log(true === 1);                  // false
52console.log(null === undefined);          // false
53
54// Best practices
55let userInput = "42";
56let numericValue = Number(userInput);     // Explicit conversion - GOOD
57// let numericValue = +userInput;         // Also explicit - GOOD
58// let numericValue = userInput * 1;      // Implicit - AVOID

Variable Scope and Hoisting in JavaScript

Scope determines where variables are accessible in your code. Hoisting is JavaScript's behavior of moving declarations to the top of their scope during compilation.

javascript
1// Global scope
2let globalVar = "I'm accessible everywhere";
3
4function demonstrateScope() {
5    // Function scope
6    let functionVar = "I'm only in this function";
7    
8    if (true) {
9        // Block scope (let/const)
10        let blockVar = "I'm only in this block";
11        const blockConst = "I'm also block-scoped";
12        var functionScopedVar = "I'm function-scoped (var)";
13        
14        console.log(globalVar);        // Accessible
15        console.log(functionVar);      // Accessible
16        console.log(blockVar);         // Accessible
17    }
18    
19    // console.log(blockVar);          // Error - blockVar not accessible
20    console.log(functionScopedVar);    // Accessible - var is function-scoped
21}
22
23// Hoisting examples
24console.log(hoistedVar);               // undefined (var is hoisted)
25var hoistedVar = "I'm hoisted";
26
27// console.log(hoistedLet);            // Error - let is hoisted but not initialized
28let hoistedLet = "I'm in temporal dead zone";
29
30// Function hoisting
31hoistedFunction();                     // Works - function declaration is hoisted
32
33function hoistedFunction() {
34    console.log("I'm hoisted!");
35}
36
37// constFunction();                    // Error - function expression not hoisted
38const constFunction = function() {
39    console.log("I'm not hoisted");
40};
41
42// Temporal Dead Zone (TDZ)
43// console.log(tdzLet);                // Error - in TDZ
44let tdzLet = "Now I'm initialized";
45
46// Lexical scope (closures)
47function outerFunction() {
48    let outerVar = "I'm outside";
49    
50    function innerFunction() {
51        console.log(outerVar);         // Can access outerVar (closure)
52    }
53    
54    return innerFunction;
55}
56
57const closureExample = outerFunction();
58closureExample();                      // "I'm outside"

Constants with Objects and Arrays

While const prevents reassignment of variables, it doesn't make objects or arrays immutable. Understanding this distinction is crucial for proper use of const.

javascript
1// Constants with primitive values
2const PI = 3.14159;
3const MAX_SIZE = 100;
4// PI = 3.14;                        // Error - cannot reassign
5
6// Constants with objects
7const person = {
8    name: "John",
9    age: 30
10};
11
12// These are ALLOWED - modifying object properties
13person.age = 31;                      // No error
14person.city = "New York";             // No error
15delete person.age;                    // No error
16
17// This is NOT allowed - reassigning the constant
18// person = { name: "Jane" };        // Error
19
20// Constants with arrays
21const colors = ["red", "green", "blue"];
22
23// These are ALLOWED - modifying array contents
24colors.push("yellow");                // No error
25colors[0] = "orange";                 // No error
26colors.pop();                         // No error
27
28// This is NOT allowed
29// colors = ["purple", "pink"];      // Error
30
31// Making objects truly immutable
32const immutablePerson = Object.freeze({
33    name: "John",
34    age: 30,
35    address: {
36        city: "Boston",
37        state: "MA"
38    }
39});
40
41// immutablePerson.age = 31;          // Error in strict mode
42// immutablePerson.newProp = "value"; // Error in strict mode
43
44// Note: Object.freeze is shallow
45immutablePerson.address.city = "Chicago"; // This WORKS - nested not frozen
46
47// Deep freeze function
48function deepFreeze(obj) {
49    Object.freeze(obj);
50    Object.getOwnPropertyNames(obj).forEach(prop => {
51        if (obj[prop] !== null && 
52            typeof obj[prop] === 'object' && 
53            !Object.isFrozen(obj[prop])) {
54            deepFreeze(obj[prop]);
55        }
56    });
57    return obj;
58}
59
60// Constants in loops
61const USERS = ["Alice", "Bob", "Charlie"];
62
63for (const user of USERS) {
64    console.log(user); // user is constant within each iteration
65    // user = "David"; // Error - cannot reassign
66}
67
68// for (const i = 0; i < 5; i++) {}  // Error - cannot reassign i
69for (let i = 0; i < 5; i++) { }       // Use let for loop counters

JavaScript Variables Best Practices

Following established best practices for variable usage leads to more maintainable, readable, and bug-free JavaScript code.

javascript
1// 1. Use const by default, let when needed
2const DEFAULT_TIMEOUT = 5000;         // GOOD - won't change
3let currentUser = null;               // GOOD - will change
4// var oldUser = null;                // AVOID - outdated
5
6// 2. Use descriptive names
7let userCount = 0;                    // GOOD - clear purpose
8let uc = 0;                          // BAD - ambiguous
9
10// 3. Initialize variables when declaring
11let username = "";                    // GOOD
12let emailAddress = null;              // GOOD - explicit null
13// let undefinedVar;                  // AVOID - implicit undefined
14
15// 4. Group related variables
16const API_CONFIG = {
17    baseUrl: "https://api.example.com",
18    timeout: 5000,
19    retries: 3
20};
21
22// 5. Avoid magic numbers
23const TAX_RATE = 0.07;
24let total = subtotal * TAX_RATE;      // GOOD
25// let total = subtotal * 0.07;       // BAD - magic number
26
27// 6. Use proper data types
28let isActive = true;                  // GOOD - boolean
29let isActive = 1;                     // BAD - number as boolean
30
31// 7. Handle type conversions explicitly
32let pageSize = Number(userInput);     // GOOD - explicit
33// let pageSize = userInput;          // BAD - implicit
34
35// 8. Use template literals for complex strings
36let welcomeMessage = `Hello ${userName}, 
37you have ${unreadCount} new messages.`;
38
39// 9. Declare variables close to their usage
40function calculateTotal(items) {
41    const TAX_RATE = 0.07;            // GOOD - close to usage
42    let subtotal = 0;
43    
44    for (let item of items) {         // GOOD - block scope
45        subtotal += item.price;
46    }
47    
48    return subtotal * (1 + TAX_RATE);
49}
50
51// 10. Avoid global variables
52// globalVar = "oops";                // BAD - accidental global
53(function() {
54    let localVar = "safe";            // GOOD - function scope
55})();
56
57// 11. Use destructuring
58const [first, second] = [1, 2, 3];
59const { name, age } = person;
60
61// 12. One variable per declaration
62let firstName = "John";               // GOOD
63let lastName = "Doe";
64// let firstName = "John", lastName = "Doe"; // AVOID - harder to read

JavaScript Variables & Data Types FAQ

What's the difference between var, let, and const?

var is function-scoped and hoisted. let and const are block-scoped. let allows reassignment, while const does not. Use const by default and let only when you need to reassign. Avoid var in modern JavaScript.

Why does typeof null return 'object'?

This is a historical bug in JavaScript that's been preserved for backward compatibility. null is actually a primitive value, not an object. Use === null to properly check for null values.

What are truthy and falsy values in JavaScript?

Falsy values: false, 0, "", null, undefined, NaN. Everything else is truthy. JavaScript uses truthy/falsy evaluation in boolean contexts like if statements and logical operators.

When should I use const with objects if they can still be modified?

Use const to indicate that the variable binding won't be reassigned, even though the object itself can be modified. This communicates intent and prevents accidental reassignment of the entire object.

What is the temporal dead zone (TDZ)?

The TDZ is the period between entering a scope and the actual declaration of a let or const variable. Accessing variables in the TDZ causes a ReferenceError. Variables are hoisted but not initialized in the TDZ.

How does JavaScript handle floating-point precision?

JavaScript uses IEEE 754 double-precision floating-point numbers, which can cause precision issues with decimal fractions. Use integer math (work in cents instead of dollars) or libraries like decimal.js for financial calculations.

What's the difference between == and ===?

== performs type coercion before comparison, while === checks both value and type without coercion. Always use === unless you specifically need type coercion, as it's more predictable and prevents bugs.

When should I use BigInt vs Number?

Use BigInt for integers larger than 2^53 - 1 (Number.MAX_SAFE_INTEGER) or when you need precise integer arithmetic beyond safe integer limits. Use Number for most numeric operations including floating-point math.