JS Objects: Dot Notation vs Bracket Notation

Understand the key differences between dot notation and bracket notation for JavaScript object property access. Learn when to use each syntax with real-world examples, performance tips, and common pitfalls.

JavaScriptbeginner
12 min read

JavaScript gives you two ways to access object properties: dot notation (obj.key) and bracket notation (obj["key"]). Both retrieve the same values, but they differ in flexibility, syntax rules, and use cases. Many beginners use them interchangeably without understanding when each one is appropriate, which leads to bugs when property names contain special characters or come from variables.

This guide explains the exact differences, shows when each notation is required, and provides real-world patterns for both.

Dot Notation Syntax

Dot notation uses a period between the object name and the property name. The property name must be a valid JavaScript identifier:

javascriptjavascript
const car = {
  make: "Toyota",
  model: "Camry",
  year: 2024,
  color: "silver"
};
 
console.log(car.make);  // "Toyota"
console.log(car.model); // "Camry"
console.log(car.year);  // 2024

Valid Identifier Rules

A property name works with dot notation only if it follows JavaScript identifier rules:

RuleValid ExamplesInvalid Examples
Starts with letter, _, or $name, _id, $price2name, -key
Contains letters, digits, _, $firstName, item_2, $totalfirst-name, item 2
Not a reserved word (mostly)status, type, valueWorks but avoid class, return
javascriptjavascript
const obj = {
  name: "Alice",        // Valid: dot works
  _id: 42,             // Valid: starts with underscore
  $price: 9.99,        // Valid: starts with dollar sign
  item2: "widget"      // Valid: digit not at start
};
 
console.log(obj.name);   // "Alice"
console.log(obj._id);    // 42
console.log(obj.$price); // 9.99

Bracket Notation Syntax

Bracket notation uses square brackets with a string expression. Any valid string (or expression that evaluates to a string) works inside the brackets:

javascriptjavascript
const car = {
  make: "Toyota",
  model: "Camry",
  year: 2024,
  "fuel-type": "hybrid",
  "0-60mph": "7.5s"
};
 
console.log(car["make"]);      // "Toyota"
console.log(car["fuel-type"]); // "hybrid"
console.log(car["0-60mph"]);   // "7.5s"

Dynamic Property Access

The key advantage of bracket notation is using variables and expressions to determine which property to access:

javascriptjavascript
const product = {
  name: "Laptop",
  price: 999,
  category: "electronics",
  brand: "TechBrand"
};
 
function getField(obj, fieldName) {
  return obj[fieldName]; // Dynamic access
}
 
console.log(getField(product, "name"));     // "Laptop"
console.log(getField(product, "price"));    // 999
console.log(getField(product, "category")); // "electronics"
 
// With computed keys
const prefix = "user";
const data = {
  userName: "alice",
  userAge: 28,
  userRole: "admin"
};
 
console.log(data[prefix + "Name"]); // "alice"
console.log(data[prefix + "Age"]);  // 28
console.log(data[`${prefix}Role`]); // "admin"

Side-by-Side Comparison

FeatureDot NotationBracket Notation
Syntaxobj.propertyobj["property"]
Dynamic keys (variables)Not supportedobj[variable]
Special charactersNot supportedobj["my-key"]
Numbers as keysNot supportedobj["123"]
Computed expressionsNot supportedobj["key" + num]
ReadabilityCleaner, shorterMore verbose
Common useStatic, known keysDynamic or special keys
Setting propertiesobj.key = valueobj["key"] = value

When Dot Notation Fails

There are specific situations where dot notation simply cannot work and bracket notation is required:

Property Names with Hyphens or Spaces

javascriptjavascript
const apiResponse = {
  "content-type": "application/json",
  "x-request-id": "abc-123",
  "rate limit": 100,
  "max-retries": 3
};
 
// Dot notation fails on these
// apiResponse.content-type    โ†’ interpreted as apiResponse.content minus type
// apiResponse.rate limit      โ†’ SyntaxError
// apiResponse.x-request-id   โ†’ interpreted as subtraction
 
// Bracket notation works perfectly
console.log(apiResponse["content-type"]);  // "application/json"
console.log(apiResponse["x-request-id"]);  // "abc-123"
console.log(apiResponse["rate limit"]);    // 100

Property Names Starting with Numbers

javascriptjavascript
const rankings = {
  "1st": "Alice",
  "2nd": "Bob",
  "3rd": "Charlie"
};
 
// Dot notation: SyntaxError
// rankings.1st
 
// Bracket notation: works fine
console.log(rankings["1st"]); // "Alice"
console.log(rankings["2nd"]); // "Bob"

Property Names from Variables

javascriptjavascript
const settings = {
  theme: "dark",
  fontSize: 16,
  language: "en"
};
 
const userChoice = "theme";
 
// WRONG: looks for a property literally named "userChoice"
console.log(settings.userChoice); // undefined
 
// CORRECT: evaluates the variable to get "theme"
console.log(settings[userChoice]); // "dark"

Real-World Patterns Using Bracket Notation

Building Objects from Form Data

javascriptjavascript
function formDataToObject(fields) {
  const result = {};
 
  for (const field of fields) {
    result[field.name] = field.value; // Dynamic key assignment
  }
 
  return result;
}
 
const formFields = [
  { name: "firstName", value: "Alice" },
  { name: "lastName", value: "Johnson" },
  { name: "email", value: "alice@example.com" }
];
 
const formData = formDataToObject(formFields);
console.log(formData);
// { firstName: "Alice", lastName: "Johnson", email: "alice@example.com" }

Config Lookup Tables

javascriptjavascript
const errorMessages = {
  404: "Page not found",
  500: "Internal server error",
  403: "Access forbidden",
  401: "Authentication required"
};
 
function getErrorMessage(statusCode) {
  return errorMessages[statusCode] || "Unknown error";
}
 
console.log(getErrorMessage(404)); // "Page not found"
console.log(getErrorMessage(500)); // "Internal server error"
console.log(getErrorMessage(999)); // "Unknown error"

Property Name Transformation

javascriptjavascript
const apiData = {
  first_name: "Alice",
  last_name: "Johnson",
  birth_date: "1998-03-15",
  phone_number: "555-0100"
};
 
// Convert snake_case to camelCase
function snakeToCamel(str) {
  return str.replace(/_([a-z])/g, (_, letter) => letter.toUpperCase());
}
 
const camelData = {};
for (const key of Object.keys(apiData)) {
  camelData[snakeToCamel(key)] = apiData[key];
}
 
console.log(camelData);
// { firstName: "Alice", lastName: "Johnson", birthDate: "1998-03-15", phoneNumber: "555-0100" }

Iterating with for...in Loops

javascriptjavascript
const userStats = {
  posts: 142,
  followers: 2840,
  following: 386,
  likes: 9200
};
 
for (const key in userStats) {
  // Bracket notation is the ONLY way to access properties dynamically in a loop
  console.log(`${key}: ${userStats[key]}`);
}
// posts: 142
// followers: 2840
// following: 386
// likes: 9200

Real-World Patterns Using Dot Notation

Object Method Chaining

Dot notation provides clean, readable method calls on objects:

javascriptjavascript
class QueryBuilder {
  constructor(table) {
    this.table = table;
    this.conditions = [];
    this.sortField = null;
    this.limitCount = null;
  }
 
  where(condition) {
    this.conditions.push(condition);
    return this;
  }
 
  orderBy(field) {
    this.sortField = field;
    return this;
  }
 
  limit(count) {
    this.limitCount = count;
    return this;
  }
 
  build() {
    let query = `SELECT * FROM ${this.table}`;
    if (this.conditions.length > 0) {
      query += ` WHERE ${this.conditions.join(" AND ")}`;
    }
    if (this.sortField) query += ` ORDER BY ${this.sortField}`;
    if (this.limitCount) query += ` LIMIT ${this.limitCount}`;
    return query;
  }
}
 
const query = new QueryBuilder("users")
  .where("age > 18")
  .where("active = true")
  .orderBy("name")
  .limit(10)
  .build();
 
console.log(query);
// "SELECT * FROM users WHERE age > 18 AND active = true ORDER BY name LIMIT 10"

Accessing Nested API Response Data

javascriptjavascript
const response = {
  status: 200,
  data: {
    user: {
      name: "Alice",
      profile: {
        avatar: "alice.jpg",
        bio: "Developer"
      }
    }
  }
};
 
// Clean, readable nested access
const avatar = response.data.user.profile.avatar;
console.log(avatar); // "alice.jpg"

Best Practices

  1. Default to dot notation for known, static property names. It is shorter, cleaner, and easier to read.
  2. Switch to bracket notation when working with dynamic keys, variables, or special-character property names.
  3. Avoid bracket notation with static strings when dot notation works. Writing user["name"] instead of user.name adds unnecessary characters.
  4. Use optional chaining (?.) with both notations when accessing properties on potentially null or undefined values.
  5. Prefer destructuring when extracting multiple properties at once. It is more readable than multiple dot or bracket accesses.
javascriptjavascript
// Good: dot notation for known keys
const name = user.name;
const age = user.age;
 
// Better: destructuring for multiple properties
const { name, age, email } = user;
 
// Good: bracket notation for dynamic keys
const value = settings[userSelectedField];
 
// Good: optional chaining for potentially missing data
const city = user?.address?.city;

Common Mistakes to Avoid

Using Dot Notation with Variables

javascriptjavascript
const key = "name";
const user = { name: "Alice" };
 
// WRONG: looks for literal property "key"
console.log(user.key); // undefined
 
// CORRECT: evaluates variable to "name"
console.log(user[key]); // "Alice"

Forgetting Quotes in Bracket Notation

javascriptjavascript
const user = { name: "Alice" };
const name = "different value";
 
// Without quotes: uses the VARIABLE named 'name'
console.log(user[name]); // undefined (looking for property "different value")
 
// With quotes: uses the STRING "name"
console.log(user["name"]); // "Alice"
Rune AI

Rune AI

Key Insights

  • Dot notation: Best for static, known property names that follow valid identifier rules
  • Bracket notation: Required for dynamic keys, special characters, numbers, and computed expressions
  • Variable access: Only bracket notation can use variables to determine which property to read
  • Both return undefined: Accessing nonexistent properties returns undefined with either notation
  • Default to dot: Use dot notation by default and switch to brackets only when necessary
RunePowered by Rune AI

Frequently Asked Questions

Is dot notation faster than bracket notation?

The performance difference is negligible in modern JavaScript engines. Both V8 (Chrome/Node.js) and SpiderMonkey (Firefox) optimize both access patterns to near-identical machine code. Choose based on readability and requirements, not performance.

Can I use bracket notation for everything and skip dot notation?

Technically yes, but it makes code less readable. `user["name"]` is harder to scan than `user.name`. Dot notation communicates at a glance that you are accessing a known, static property. Reserve bracket notation for cases where it provides actual value: dynamic access, special characters, or computed keys.

How does property access work with [arrays](/tutorials/programming-languages/javascript/what-is-an-array-in-javascript-a-complete-guide)?

rrays are objects, so both notations work. Numeric indices use bracket notation: `arr[0]`. Array methods and properties use dot notation: `arr.length`, `arr.push()`. You cannot use dot notation with numeric indices because `arr.0` is a syntax error.

What happens if I access a property that does not exist?

Both notations return `undefined` for nonexistent properties. They do not throw errors. However, accessing a property on `null` or `undefined` itself throws a [TypeError](/tutorials/programming-languages/javascript/basic-javascript-debugging-tips-for-beginners). Use optional chaining (`?.` or `?.[]`) to guard against this.

Can bracket notation use non-string values?

JavaScript automatically converts the bracket expression to a string. Numbers, booleans, and other values are coerced: `obj[42]` becomes `obj["42"]`, and `obj[true]` becomes `obj["true"]`. Symbol keys are the only exception; they remain as symbols.

Conclusion

Dot notation and bracket notation both access object properties, but they serve different roles. Dot notation is your everyday choice for static, known property names because of its clean, readable syntax. Bracket notation steps in when you need dynamic access, computed keys, or property names with special characters. Most JavaScript code uses dot notation about 80% of the time, switching to bracket notation only when the situation requires it.