Objects

JavaScript · Lesson 23 of 61 7 min read Updated

A student has a name, a roll number, a city and marks in five subjects. You could store each detail in its own variable, but they belong together. An object groups related values under one name, with a label for each value. Almost everything in JavaScript is built from objects: arrays, dates, the web page itself.

In this lesson you will create objects, read and change their values, add functions to them, loop over them, and learn how to copy an object without surprises.

Creating an object

The simplest way to make an object is an object literal: curly braces containing key: value pairs separated by commas. Each pair is called a property. The key is the label, and the value can be anything: a string, a number, an array, a function or another object.

JavaScriptRun it yourself
const student = {
  name: "Priya Nair",
  city: "Kochi",
  rollNo: 23,
  isHosteller: false,
};

console.log(student.name);
console.log(student["city"]);

const field = "rollNo";
console.log(student[field]);
console.log(student.phone);
Output
Priya Nair
Kochi
23
undefined

There are two ways to read a property:

  • Dot notation, student.name, is short and used most of the time.
  • Bracket notation, student["city"], takes the key as a string. Use it when the key is stored in a variable, like field above, or when the key contains a space or a hyphen, such as obj["pin-code"].

Reading a property that does not exist gives undefined, not an error. The comma after the last property, called a trailing comma, is allowed and makes adding a new line later cleaner.

Adding, changing and deleting properties

Objects can change after you create them, even when stored in a const, because const only fixes which object the name points to.

JavaScriptRun it yourself
const product = { name: "Cotton kurta", price: 799 };

product.price = 699;        // change
product.size = "M";         // add
product.colour = "Indigo";  // add
delete product.colour;      // remove

console.log(product);
console.log("size" in product);
console.log(Object.hasOwn(product, "colour"));
Output
{ name: 'Cotton kurta', price: 699, size: 'M' }
true
false

To check whether a property exists, use "key" in obj or Object.hasOwn(obj, "key"). Checking obj.key !== undefined fails when a property exists but holds undefined. The difference between in and Object.hasOwn() is that in also finds inherited properties, which you will learn about in Inheritance & Prototypes.

Methods

A function stored in an object is called a method. Modern JavaScript has a short way to write methods, without the colon and the word function:

JavaScriptRun it yourself
const account = {
  owner: "Rohan",
  balance: 2000,
  deposit(amount) {
    this.balance += amount;
    return `${this.owner} now has ₹${this.balance}`;
  },
};

console.log(account.deposit(500));
console.log(account.deposit(250));
Output
Rohan now has ₹2500
Rohan now has ₹2750

Inside a method, this refers to the object the method was called on, so this.balance is account.balance. this has some tricky rules, explained in The this Keyword. Do not use arrow functions for methods that need this, as you saw in Arrow Functions. When you need many objects of the same shape, such as a thousand accounts, use a class, covered in Classes.

Shorthand properties and computed keys

Two shortcuts appear in nearly every modern codebase:

JavaScriptRun it yourself
const customer = "Meera";
const city = "Lucknow";

const user = { customer, city };   // same as { customer: customer, city: city }
console.log(user);

const key = "favouriteSweet";
const prefs = { [key]: "Kaju katli" }; // the key is calculated
console.log(prefs);
Output
{ customer: 'Meera', city: 'Lucknow' }
{ favouriteSweet: 'Kaju katli' }

When a variable has the same name as the key, write it once. When the key itself comes from a variable or an expression, put it in square brackets; this is called a computed key.

Nested objects and arrays of objects

Real data is usually nested: objects inside objects, and arrays of objects.

JavaScript
const order = {
  id: 5012,
  customer: { name: "Farhan", city: "Lucknow" },
  items: [
    { name: "Veg biryani", qty: 2 },
    { name: "Raita", qty: 1 },
  ],
};

console.log(order.customer.name);   // "Farhan"
console.log(order.items[0].name);   // "Veg biryani"
console.log(order.items.length);    // 2

Read the path from left to right: order.items[0].name means "in order, take items, take the first one, take its name". This is exactly the shape of data you get from web servers in JSON format, covered in JSON.

Looping over an object

Object.keys(), Object.values() and Object.entries() turn an object into arrays, which you can loop over or use with array methods. Object.fromEntries() does the opposite and builds an object from [key, value] pairs.

JavaScriptRun it yourself
const prices = { tea: 15, coffee: 25, lassi: 40 };

for (const [item, price] of Object.entries(prices)) {
  console.log(`${item}: ₹${price}`);
}

const newPrices = Object.fromEntries(
  Object.entries(prices).map(([item, price]) => [item, price + 5]),
);
console.log(newPrices);
Output
tea: ₹15
coffee: ₹25
lassi: ₹40
{ tea: 20, coffee: 30, lassi: 45 }

The second part raises every price by ₹5: convert to pairs, change each pair with map(), and convert back. The loop syntax itself is explained in for...of and for...in.

Copying objects

Like arrays, objects are shared, not copied, when you assign them. To copy, you have two tools:

JavaScriptRun it yourself
const original = { name: "Kabir", marks: { maths: 90 } };

const shallow = { ...original };
const deep = structuredClone(original);

original.marks.maths = 95;

console.log(shallow.marks.maths);
console.log(deep.marks.maths);
Output
95
90
  • The spread syntax { ...original } makes a shallow copy: a new outer object, but nested objects are still shared. That is why shallow.marks.maths changed too. Spread is covered in Destructuring, Rest & Spread.
  • structuredClone() makes a deep copy: every nested level is copied, so deep is completely independent. It cannot copy functions, so use it for plain data.

If you want an object that nobody can change, Object.freeze(obj) locks its top-level properties. In strict mode, which modules use, trying to change a frozen property throws an error.

Common mistakes

  • Dot notation with a variable. obj.key looks for a property literally named "key". Use obj[key].
  • Thinking const freezes the object. It does not; properties can still change.
  • Expecting spread to copy nested data. { ...obj } is shallow. Use structuredClone() for a full copy.
  • Reading deep into data that may be missing. order.customer.address.city throws if address is missing. Use ?..
  • Arrow functions as methods. They do not get the object as this. Use method() { }.

Key points

  • An object stores related values as key: value properties inside { }.
  • Read properties with obj.key or obj["key"]; use brackets for variable or unusual keys.
  • Properties can be added, changed and removed; in and Object.hasOwn() check for them.
  • Methods are functions in objects; inside them, this is the object.
  • Object.keys(), values(), entries() and fromEntries() convert between objects and arrays.
  • Assignment shares an object; { ...obj } copies one level, structuredClone() copies all levels.

Exercise

Create an object for a mobile phone in a Pune shop with brand, model, price and stock, and a method sell(qty) that reduces the stock and returns "Sold X, Y left", or returns "Only Y in stock" if there are not enough. Sell 2 phones, then try to sell 10. Finally, print all keys of the object with Object.keys().

Show solution
JavaScript
const phone = {
  brand: "Sunrise",
  model: "S10 5G",
  price: 12999,
  stock: 5,
  sell(qty) {
    if (qty > this.stock) {
      return `Only ${this.stock} in stock`;
    }
    this.stock -= qty;
    return `Sold ${qty}, ${this.stock} left`;
  },
};

console.log(phone.sell(2));
console.log(phone.sell(10));
console.log(Object.keys(phone));
Output
Sold 2, 3 left
Only 3 in stock
[ 'brand', 'model', 'price', 'stock', 'sell' ]

The method uses this.stock, so it always works with the object it belongs to. Methods are properties too, which is why sell appears in the list of keys.

Quick Quiz

1. Given const key = "city";, which expression reads the city property of user?

2. What does reading a property that does not exist return?

3. What does { city } mean when a variable city already exists?

4. Which line makes a copy where even nested objects are independent?

Learn JavaScript with a mentor

Free lessons get you started. Our Full Stack Web Development training adds real projects and code reviews from working developers.

  • Project-based learning
  • Mentor code reviews
  • Free counselling call