Инициализатор объекта
Базовый уровень Широко доступно
Эта функция хорошо зарекомендовала себя и работает на многих устройствах и в разных версиях браузеров. Она доступна во всех браузерах с июля 2015 года.
Инициализатор объекта — это разделённый запятыми список из нуля или более пар имён свойств и связанных с ними значений объекта, заключённый в фигурные скобки ({}). Объекты также могут быть инициализированы с помощью Object.create() или путём вызова функции-конструктора с оператором new.
Попробуйте
const object1 = { a: "foo", b: 42, c: {} };
console.log(object1.a);
// Expected output: "foo"
const a = "foo";
const b = 42;
const c = {};
const object2 = { a: a, b: b, c: c };
console.log(object2.b);
// Expected output: 42
const object3 = { a, b, c };
console.log(object3.a);
// Expected output: "foo"
Синтаксис
o = {
a: "foo",
b: 42,
c: {},
1: "number literal property",
"foo:bar": "string literal property",
shorthandProperty,
method(parameters) {
// …
},
get property() {},
set property(value) {},
[expression]: "computed property",
__proto__: prototype,
...spreadProperty,
};
Описание
Инициализатор объекта — это выражение, которое описывает инициализацию Object. Объекты состоят из свойств, которые используются для описания объекта. Значения свойств объекта могут содержать либо примитивные типы данных, либо другие объекты.
Синтаксис объектных литералов против JSON
Синтаксис объектных литералов не то же самое, что JavaScript Object Notation (Объектная нотация JavaScript, JSON). Хотя они выглядят схоже, между ними есть различия:
- JSON только разрешает определение свойств с использованием синтаксиса
"property": value. Имя свойства должно быть заключено в двойные кавычки, а определение не может быть сокращённым. Вычисляемые имена свойств также не допускаются. - Значения свойств объекта JSON могут быть только строками, числами,
true,false,null, массивами или другим объектом JSON. Это означает, что JSON не может выражать методы или не-простые объекты, такие какMapилиRegExp. - В JSON,
"__proto__"является обычным ключом свойства. В объектном литерале он устанавливает прототип объекта.
JSON является строгим подмножеством синтаксиса объектных литералов, что означает, что любой допустимый текст JSON может быть проанализирован как объектный литерал и, вероятно, не вызовет синтаксических ошибок. Единственное исключение состоит в том, что синтаксис объектных литералов запрещает дублирующиеся ключи __proto__, что не относится к JSON.parse(). Последний обрабатывает __proto__ как обычное свойство и принимает последнее вхождение в качестве значения свойства. Единственный раз, когда представляемое ими значение объекта (т. е. их семантика) различается, это также, когда исходный код содержит ключ __proto__ — для объектных литералов он устанавливает прототип объекта; для JSON это обычное свойство.
console.log(JSON.parse('{ "__proto__": 0, "__proto__": 1 }')); // {__proto__: 1}
console.log({ "__proto__": 0, "__proto__": 1 }); // SyntaxError: Duplicate __proto__ fields are not allowed in object literals
console.log(JSON.parse('{ "__proto__": {} }')); // { __proto__: {} }
console.log({ "__proto__": {} }); // {} (with {} as prototype)
Примеры
Создание объектов
Пустой объект без свойств может быть создан следующим образом:
const object = {};
Однако преимущество литеральной нотации или нотации инициализатора состоит в том, что вы можете быстро создавать объекты со свойствами внутри фигурных скобок. Вы обозначаете список пар key: value, разделённых запятыми.
Следующий код создаёт объект с тремя свойствами, ключами которых являются "foo", "age" и "baz". Значениями этих ключей являются строка "bar", число 42 и другой объект.
const object = {
foo: "bar",
age: 42,
baz: { myProp: 12 },
};
Доступ к свойствам
После создания объекта вы, возможно, захотите прочитать или изменить их. Доступ к свойствам объекта может осуществляться с использованием точечной нотации или скобочной нотации. (Подробную информацию смотрите в разделе методы доступа к свойствам.)
object.foo; // "bar"
object["age"]; // 42
object.baz; // {myProp: 12}
object.baz.myProp; // 12
Определения свойств
Мы уже узнали, как обозначать свойства, используя синтаксис инициализатора. Часто в вашем коде есть переменные, которые вы хотели бы поместить в объект. Вы увидите код, подобный этому:
const a = "foo";
const b = 42;
const c = {};
const o = {
a: a,
b: b,
c: c,
};
Для достижения того же результата доступна более короткая нотация:
const a = "foo";
const b = 42;
const c = {};
// Shorthand property names
const o = { a, b, c };
// In other words,
console.log(o.a === { a }.a); // true
Дублирующиеся имена свойств
При использовании одинаковых имён для ваших свойств второе свойство перезапишет первое.
const a = { x: 1, x: 2 };
console.log(a); // {x: 2}
После ES2015 дублирующиеся имена свойств разрешены везде, включая строгий режим. Вы также можете иметь дублирующиеся имена свойств в классах. Единственным исключением являются приватные элементы, которые должны быть уникальными в теле класса.
Определения методов
Свойство объекта также может ссылаться на функцию, метод получения (getter) или метод установки (setter).
const o = {
property: function (parameters) {},
get property() {
return 1;
},
set property(value) {},
};
Доступна сокращённая нотация, так что ключевое слово function больше не требуется.
// Shorthand method names
const o = {
property(parameters) {},
};
Существует также способ кратко определить методы-генераторы.
const o = {
*generator() {
// …
},
};
Что эквивалентно нотации, подобной ES5 (но обратите внимание, что в ECMAScript 5 нет генераторов):
const o = {
generator: function* () {
// …
},
};
Для получения дополнительной информации и примеров о методах смотрите определения методов.
Вычисляемые имена свойств
Синтаксис инициализатора объекта также поддерживает вычисляемые имена свойств. Это позволяет вам поместить выражение в квадратные скобки [], которое будет вычислено и использовано в качестве имени свойства. Это напоминает скобочную нотацию синтаксиса доступа к свойствам, которую вы, возможно, уже использовали для чтения и установки свойств.
Теперь вы можете использовать аналогичный синтаксис и в объектных литералах:
// Computed property names
let i = 0;
const a = {
[`foo${++i}`]: i,
[`foo${++i}`]: i,
[`foo${++i}`]: i,
};
console.log(a.foo1); // 1
console.log(a.foo2); // 2
console.log(a.foo3); // 3
const items = ["A", "B", "C"];
const obj = {
[items]: "Hello",
};
console.log(obj); // A,B,C: "Hello"
console.log(obj["A,B,C"]); // "Hello"
const param = "size";
const config = {
[param]: 12,
[`mobile${param.charAt(0).toUpperCase()}${param.slice(1)}`]: 4,
};
console.log(config); // {size: 12, mobileSize: 4}
Свойства расширения
Объектные литералы поддерживают синтаксис расширения. Он копирует собственные перечисляемые свойства из предоставленного объекта в новый объект.
Поверхностное клонирование (исключая prototype) или слияние объектов теперь возможно с использованием более короткого синтаксиса, чем Object.assign().
const obj1 = { foo: "bar", x: 42 };
const obj2 = { foo: "baz", y: 13 };
const clonedObj = { ...obj1 };
// { foo: "bar", x: 42 }
const mergedObj = { ...obj1, ...obj2 };
// { foo: "baz", x: 42, y: 13 }
Предупреждение: Обратите внимание, что Object.assign() вызывает сеттеры, тогда как синтаксис расширения — нет!
Установщик прототипа
Определение свойства в форме __proto__: value или "__proto__": value не создаёт свойства с именем __proto__. Вместо этого, если предоставленное значение является объектом или null, оно указывает [[Prototype]] созданного объекта на это значение. (Если значение не является объектом или null, объект не изменяется.)
Обратите внимание, что ключ __proto__ является стандартизированным синтаксисом, в отличие от нестандартных и неэффективных методов доступа Object.prototype.__proto__. Он устанавливает [[Prototype]] во время создания объекта, аналогично Object.create — вместо изменения цепочки прототипов.
const obj1 = {};
console.log(Object.getPrototypeOf(obj1) === Object.prototype); // true
const obj2 = { __proto__: null };
console.log(Object.getPrototypeOf(obj2)); // null
const protoObj = {};
const obj3 = { "__proto__": protoObj };
console.log(Object.getPrototypeOf(obj3) === protoObj); // true
const obj4 = { __proto__: "not an object or null" };
console.log(Object.getPrototypeOf(obj4) === Object.prototype); // true
console.log(Object.hasOwn(obj4, "__proto__")); // false
В объектном литерале разрешён только один установщик прототипа. Несколько установщиков прототипов являются синтаксической ошибкой.
Определения свойств, которые не используют «двоеточие», не являются установщиками прототипов. Это определения свойств, которые ведут себя идентично аналогичным определениям с использованием любого другого имени.
const __proto__ = "variable";
const obj1 = { __proto__ };
console.log(Object.getPrototypeOf(obj1) === Object.prototype); // true
console.log(Object.hasOwn(obj1, "__proto__")); // true
console.log(obj1.__proto__); // "variable"
const obj2 = { __proto__() { return "hello"; } };
console.log(obj2.__proto__()); // "hello"
const obj3 = { ["__proto__"]: 17 };
console.log(obj3.__proto__); // 17
// Mixing prototype setter with normal own properties with "__proto__" key
const obj4 = { ["__proto__"]: 17, __proto__: {} }; // {__proto__: 17} (with {} as prototype)
const obj5 = {
["__proto__"]: 17,
__proto__: {},
__proto__: null, // SyntaxError: Duplicate __proto__ fields are not allowed in object literals
};
const obj6 = {
["__proto__"]: 17,
["__proto__"]: "hello",
__proto__: null,
}; // {__proto__: "hello"} (with null as prototype)
const obj7 = {
["__proto__"]: 17,
__proto__,
__proto__: null,
}; // {__proto__: "variable"} (with null as prototype)
Спецификации
Совместимость с браузерами
| Десктопные | Мобильные | Серверные | |||||||||||||
|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|
| Chrome | Edge | Firefox | Opera | Safari | Chrome Android | Firefox for Android | Opera Android | Safari on iOS | Samsung Internet | WebView Android | WebView on iOS | Bun | Deno | Node.js | |
object_initializer |
1 |
12 |
1 |
4 |
1 |
18 |
4 |
10.1 |
1 |
1.0 |
4.4 |
1 |
1.0.0 |
1.0 |
0.10.0 |
computed_property_names |
47 |
12 |
34 |
34 |
8 |
47 |
34 |
34 |
8 |
5.0 |
47 |
8 |
1.0.0 |
1.0 |
4.0.0 |
shorthand_method_names |
47 |
12 |
34 |
34 |
9 |
47 |
34 |
34 |
9 |
5.0 |
47 |
9 |
1.0.0 |
1.0 |
4.0.0 |
shorthand_property_names |
47 |
12 |
33 |
34 |
9 |
47 |
33 |
34 |
9 |
5.0 |
47 |
9 |
1.0.0 |
1.0 |
4.0.0 |
spread_properties |
60 |
79 |
55 |
47 |
11.1 |
60 |
55 |
44 |
11.3 |
8.0 |
60 |
11.3 |
1.0.0 |
1.0 |
8.3.0 |
Смотрите также
© 2005–2025 MDN contributors.
Licensed under the Creative Commons Attribution-ShareAlike License v2.5 or later.
https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Operators/Object_initializer