Объект и ссылка на него13 / 19

Изменить объект или заменить ссылку?

Чем изменение свойства отличается от присваивания переменной и что запрещает const.

В предыдущем уроке мы рассмотрели две переменные, которые ссылаются на один объект. Теперь сравним два действия: изменить свойство объекта и присвоить переменной другое значение.

const player = { hp: 100 };
let target = player;
target.hp = 50;
target = null;
// player.hp is 50; the object is still reachable
  1. const player = { hp: 100 } создаёт объект и сохраняет ссылку на него в player.
  2. let target = player присваивает target то же объектное значение. В обеих переменных теперь ссылки на один объект. Это не ссылка target на переменную player: каждая переменная даёт доступ к объекту самостоятельно.
  3. target.hp = 50 обращается к объекту по ссылке из target и записывает новое значение в свойство hp. Меняется общий объект, поэтому и target.hp, и player.hp теперь равны 50.
  4. target = null заменяет значение только переменной target. Теперь в ней null вместо ссылки. Значение player и сам объект не меняются; объект по-прежнему доступен через player.
Изменили свойствоtarget.hp = 50
player
Объект игрока{ hp: 50 }
target

Свойство изменилось. Обе ссылки сохранились.

Изменили переменнуюtarget = null
player
Тот же объект{ hp: 50 }
target
null

target больше не ведёт к объекту. player по-прежнему ведёт.

Два последовательных состояния одной программы. Во втором состоянии объект тот же: изменилось только значение target.

Выполнение по строкам

Интерактивная схема. #1 — условная метка объекта, не адрес памяти.

  1. const player = { hp: 100 }; Следующая
  2. let target = player;
  3. target.hp = 50;
  4. target = null;

Переменные

playerСтрока ещё не выполнена
targetСтрока ещё не выполнена

Heap · куча

Объект примера ещё не создан
player.hp
—
target.hp
—

Строки примера ещё не выполнены. Начнём с создания объекта.

Выполнено 0 из 4
Основной вывод
  1. Переменная с объектным значением даёт доступ к объекту через ссылку. Присваивание этого значения другой переменной копирует ссылку, а не объект.
  2. Изменение свойства меняет общий объект. Присваивание переменной другого значения заменяет только её собственную ссылку и не меняет остальные ссылки или объект.
  3. const запрещает заменять значение переменной, но не делает сам объект неизменяемым.

Проверить по первоисточнику ↗

ECMA-262 · Object Type↗Объект состоит из свойств; чтение и изменение свойства — операции над самим объектом.ECMA-262 · Let and Const Declarations↗Объявление переменных через let и const и присваивание начального значения.ECMA-262 · SetMutableBinding↗Присваивание меняет значение конкретной переменной; попытка заменить значение const приводит к TypeError.ECMA-262 · GetValue / PutValue↗Чтение значения и различие между записью свойства объекта и присваиванием переменной.V8 · Pointer Compression↗Внутреннее представление ссылок на объекты: указатели и сжатые смещения вместо доступных JavaScript числовых адресов.V8 · Moving objects and updating pointers↗При перемещении объектов сборщик V8 обновляет указывающие на них ссылки.