<b> return о;</b>
<b>}</b>
<b>/*</b>
<b>* Возвращает новый объект, содержащий свойства, присутствующие хотя бы в одном</b>
<b>* из объектов, о или р. Если оба объекта, о и р, имеют свойства с одним</b>
<b>* и тем же именем, используется значение свойства из объекта р.</b>
<b>*/</b>
<b>function union(o,p) { return extend(extend({},о), p); }</b>
<b>/*</b>
<b>* Возвращает новый объект, содержащий свойства, присутствующие сразу в обоих</b>
<b>* объектах, о или р. Результат чем-то напоминает пересечение о и р,</b>
<b>* но значения свойств объекта р отбрасываются */</b>
<b>function intersection(o, р) { return restrict(extend({}, о), р); }</b>
<b>/*</b>
<b>* Возвращает массив имен собственных перечислимых свойств объекта о.</b>
<b>*/</b>
<b>function keys(o) {</b>
<b> if (typeof о !== "object”) throw ТуреЕггогО; // Apr. должен быть объектом </b>
<b> var result = []; // Возвращаемый массив</b>
<b> for(var prop in о) { // Для всех перечислимых свойств</b>
<b> if (о.hasOwnProperty(prop)) // Если это собственное свойство,</b>
<b> result.push(prop); // добавить его в массив array.</b>
<b> }</b>
<b> return result; // Вернуть массив.</b>
<b>}</b>
В дополнение к циклу
<b>for/in</b>
стандарт ECMAScript 5 определяет две функции, перечисляющие имена свойств. Первая из них,
<b>Object.keys(),</b>
возвращает массив имен собственных перечислимых свойств объекта. Она действует аналогично функции
<b>keys()</b>
из примера 6.2.
Вторая функция ECMAScript 5, выполняющая перечисление свойств, -
<b>Object.getOwnPropertyNames().</b>
Она действует подобно функции
<b>Object.keys(),</b>
но возвращает имена всех собственных свойств указанного объекта, а не только перечислимые. В реализациях ECMAScript 3 отсутствует возможность реализовать подобные функции, потому что ECMAScript 3 не предусматривает возможность получения неперечислимых свойств объекта.
6.6. Методы чтения и записи свойств
Выше уже говорилось, что свойство объекта имеет имя, значение и набор атрибутов. В ECMAScript 5[10]
значение может замещаться одним или двумя методами, известными как методы чтения (
<b>getter</b>
) и записи (
<b>setter</b>
). Свойства, для которых определяются методы чтения и записи, иногда называют свойствами с методами доступа, чтобы отличать их от свойств с данными, представляющих простое значение.
Когда программа пытается получить значение свойства с методами доступа, интерпретатор вызывает метод чтения (без аргументов). Возвращаемое этим методом значение становится значением выражения обращения к свойству. Когда программа пытается записать значение в свойство, интерпретатор вызывает метод записи, передавая ему значение, находящее справа от оператора присваивания. Этот метод отвечает за «установку» значения свойства. Значение, возвращаемое методом записи, игнорируется.
В отличие от свойств с данными, свойства с методами доступа не имеют атрибута
<b>writable</b>
. Если свойство имеет оба метода, чтения и записи, оно доступно для чтения/записи. Если свойство имеет только метод чтения, оно доступно только для чтения. А если свойство имеет только метод записи, оно доступно только для записи (такое невозможно для свойств с данными) и попытки прочитать значение такого свойства всегда будут возвращать
<b>undefined</b>
.
Самый простой способ определить свойство с методами доступа заключается в использовании расширенного синтаксиса определения литералов объектов:
<b>var о = {</b>
<b> // Обычное свойство с данными </b>
<b> data_prop: value,</b>
<b> // Свойство с методами доступа определяется как пара функций </b>
<b> get accessor_prop() { /* тело функции */ }, </b>
<b> set accessor_prop(value) { /* тело функции */ }</b>
<b>};</b>
Свойства с методами доступа определяются как одна или две функции, имена которых совпадают с именем свойства и с заменой ключевого слова
<b>function</b>
на
<b>ge</b>
t и/или
<b>set</b>
. Обратите внимание, что не требуется использовать двоеточие для отделения имени свойства от функции, управляющей доступом к свойству, но по-прежнему необходимо использовать запятую после тела функции, чтобы отделить метод от других методов или свойств с данными. Для примера рассмотрим следующий объект, представляющий Декартовы координаты точки на плоскости. Для представления координат X и Y в нем имеются обычные свойства с данными, а также свойства с методами доступа, позволяющие получить эквивалентные полярные координаты точки:
<b>var р = {</b>
<b> // х и у - обычные свойства с данными, доступные для чтения/записи. </b>
<b> х: 1.0,</b>
<b> у: 1.0,</b>
<b> //r - доступное для чтения/записи свойство с двумя методами доступа. </b>
<b> // Не забывайте добавлять запятые после методов доступа, </b>
<b> get r() { return Math.sqrt(this.x*this.x + this.y*this.y); }, </b>