Додавання властивості до об'єкта
Нову властивість додають простим присвоєнням через крапку або квадратні дужки, а коли потрібно більше контролю, використовують Object.assign(), spread-синтаксис або Object.defineProperty(). Вибір способу зводиться до двох питань: чи ключ відомий заздалегідь і чи можна змінювати початковий об'єкт.
Теорія
TL;DR
obj.key = value, найпростіший спосіб, працює для валідних ідентифікаторів.obj['key'] = value, потрібен для динамічних ключів і імен зі спецсимволами.Object.assign(target, source)додає кілька властивостей одразу і змінюєtarget.{ ...obj, key: value }створює новий об'єкт, початковий лишається незмінним.Object.defineProperty()дає повний контроль над дескриптором властивості.constне забороняє додавати властивості: він фіксує саме посилання, а не вміст об'єкта.
Швидкий приклад
const user = { name: 'Maria' };
user.age = 25; // крапка
user['city'] = 'Kyiv'; // дужки
console.log(user);
// { name: 'Maria', age: 25, city: 'Kyiv' }Крапка і квадратні дужки
Через крапку (.):
const user = { name: 'Maria' };
user.age = 25; // додаємо нову властивість
console.log(user);
// { name: 'Maria', age: 25 }Працює, якщо ім'я властивості є валідним ідентифікатором: без пробілів, без спецсимволів, не починається з цифри.
Через квадратні дужки ([]):
const user = { name: 'Maria' };
user['city'] = 'Kyiv';
console.log(user);
// { name: 'Maria', city: 'Kyiv' }Цей спосіб підходить, якщо ключ зберігається у змінній:
const key = 'email';
user[key] = 'maria@example.com';або містить невалідні символи:
user['favorite color'] = 'blue';Object.assign()
const user = { name: 'Maria' };
Object.assign(user, { age: 25, city: 'Kyiv' });
console.log(user);
// { name: 'Maria', age: 25, city: 'Kyiv' }Можна одразу додати кілька властивостей. Метод змінює початковий об'єкт (перший аргумент) і повертає його ж. Копіювання поверхневе: вкладені об'єкти переносяться за посиланням.
Spread-синтаксис
const user = { name: 'Maria' };
const updatedUser = { ...user, age: 25 };
console.log(updatedUser);
// { name: 'Maria', age: 25 }Початковий об'єкт не змінюється, створюється нова копія. Це імутабельний спосіб, саме він потрібен у React, Redux і будь-де, де порівняння стану йде за посиланням. Якщо ключ повторюється, виграє той, що записаний пізніше, тож { ...user, name: 'Oleh' } перезапише ім'я.
Object.defineProperty()
const user = {};
Object.defineProperty(user, 'age', {
value: 25,
writable: true,
enumerable: true,
configurable: true
});
console.log(user); // { age: 25 }Дозволяє точно налаштувати властивість: зробити її, наприклад, тільки для читання (writable: false) або прихованою при переборі (enumerable: false). Важливо: якщо прапорці не вказати явно, усі три за замовчуванням дорівнюють false, на відміну від звичайного присвоєння.
Порівняння способів
| Спосіб | Змінює початковий об'єкт | Підходить для |
|---|---|---|
obj.key = value | Так | прості випадки |
obj['key'] = value | Так | динамічні ключі |
Object.assign() | Так | масове додавання |
{ ...obj, key: value } | Ні | створення нового об'єкта |
Object.defineProperty() | Так | особливі налаштування властивості |
Типові помилки
- Думати, що
constзабороняє додавати властивості.const user = {}фіксує посилання, а не вміст:user.age = 25спрацює. Щоб заборонити зміни, потрібніObject.freeze()абоObject.seal(). - Використовувати крапку зі змінною.
user.key = 1створить властивість з іменем"key", а не значення змінноїkey. Для змінної потрібні дужки:user[key] = 1. - Вважати
Object.assign()глибоким копіюванням. Воно поверхневе: вкладені об'єкти лишаються спільними. Для глибокої копії берітьstructuredClone(). - Забувати прапорці в
Object.defineProperty(). Без явнихwritable,enumerable,configurableвластивість буде нередаговною і невидимою дляObject.keys()таJSON.stringify(). - Мутувати об'єкт там, де очікують нове посилання. Якщо стан порівнюється за посиланням, пряме присвоєння не спричинить оновлення, потрібен spread.
Коротка відповідь
Для співбесідиКоротка відповідь допоможе вам впевнено відповідати на цю тему під час співбесіди.