Книга: JavaScript. Подробное руководство, 6-е издание

9.6.3. Стандартные методы преобразований

9.6.3. Стандартные методы преобразований

В разделах 3.8.3 и 6.10 описываются важные методы, используемые для преобразования типа объектов, часть из которых автоматически вызывается интерпретатором JavaScript по мере необходимости. Вам не обязательно определять эти методы в каждом своем классе, но они играют важную роль, и если вы отказываетесь от их реализации в своих классах, это должен быть осознанный выбор, а не простая оплошность.

Первым и наиболее важным является метод toString(). Назначение этого метода в том, чтобы возвращать строковое представление объекта. Интерпретатор JavaScript автоматически вызывает этот метод, когда объект используется там, где ожидается строка - в качестве имени свойства, например, или с оператором +, выполняющим конкатенацию строк. Если отказаться от реализации этого метода, ваш класс унаследует от Object.prototype реализацию по умолчанию и будет преобразовываться в довольно бесполезную строку «[object Object]». Метод toString() может возвращать более удобочитаемую строку, подходящую для отображения на экране перед конечным пользователем вашего приложения. Однако даже если в этом нет необходимости, часто бывает полезно определить свой метод toString(), чтобы упростить отладку. Классы Range и Complex, представленные в примерах 9.2 и 9.3, имеют собственные реализации метода toString(), как и типы-перечисления, реализация которых приводится в примере 9.7. Ниже мы определим метод, toString() для класса Set из примера 9.6.

С методом toString() тесно связан метод toLocaleString(): он должен преобразовывать объект в строку с учетом региональных настроек. По умолчанию объекты наследуют метод toLocaleString(), который просто вызывает их метод toString(). Некоторые встроенные типы имеют более полезные реализации метода toLocaleString(), которые возвращают строки с учетом региональных настроек. Если в реализации своего метода toString() вам придется преобразовывать в строки другие объекты, вы также должны определить свой метод toLocaleString(), выполняющий те же преобразования вызовом метода toLocaleString() объектов. Ниже мы реализуем этот метод для класса Set.

Третьим методом является метод valueOf(). Его цель - преобразовать объект в простое значение. Метод valueOf() вызывается автоматически, когда объект используется в числовом контексте, например, с арифметическими операторами (отличными от +) и с операторами отношения. Большинство объектов не имеют сколько-нибудь осмысленного простого представления и потому не определяют этот метод. Однако типы-перечисления в примере 9.7 представляют случай, когда метод valueOf() имеет большое значение.

Четвертый метод - toJSON() - вызывается автоматически функцией JSON.stringifу(). Формат JSON предназначен для сериализации структур данных и может использоваться для представления простых значений, массивов и простых объектов. При преобразовании в этот формат не делается никаких предположений о классах, и при сериализации объекта игнорируются его прототип и конструктор. Если вызвать функцию JSON.stringify() для сериализации объекта Range или Complex, например, она вернет строку вида {"from”: 1, ”to":3} или {"r":1, "i":-1}. Если передать такую строку функции JSON.parse(), она вернет простой объект со свойствами, соответствующими объекту Range или Complex, но не наследующий методы класса Range или Complex.

Такой формат сериализации вполне подходит для классов, таких как Range и Complex, но для более сложных классов может потребоваться написать собственный метод toJSON(), чтобы определить иной формат сериализации. Если объект имеет метод toJSON(), функция JSON.stringify() не будет выполнять сериализацию самого объекта, а вызовет метод toJSON() и произведет сериализацию значения (простого значения или объекта), которое он вернет. Например, объекты Date имеют собственный метод toJSON(), возвращающий строковое представление даты. Типы-перечисления в примере 9.7 делают то же самое: их метод toJS0N() возвращает то же значение, что и метод toString(). Самым близким к представлению множества в формате JSON является массив, поэтому ниже мы определим метод toJSON(), который будет преобразовывать объект Set в массив значений.

Класс Set, представленный в примере 9.6, не определяет ни один из этих методов. Множество не может быть представлено простым значением, поэтому нет смысла определять метод valueOf(), но было бы желательно определить в этом классе методы toString(), toLocaleString() и toJSON(). Можно это сделать, как показано ниже. Обратите внимание, что для добавления методов в Set.prototype используется функция extend() (пример 6.2):

// Добавить новые методы в объект-прототип класса Set.
extend(Set.prototype, {
  // Преобразует множество в строку
  toString : function() {
    var s = "{", i = 0;
    this.foreach(function(v){ s += ((i++ > 0)?", + ":"") +v });
    return s + "}";
  }
  // Действует так же, как toString, но вызывает toLocaleString
  // для всех значений
  toLocaleString : function() {
    var s = "{", і = 0;
    this.foreach(function(v){
      if (i++ > 0) s += ", ";
      if (v == null) s += v; // null и undefined
      else s += v. toLocaleString(); // остальные
    });
    return s +
  },
  // Преобразует множество в массив значений
  toArray : function() {
    var a = [];
    this.foreach(function(v) { a.push(v); });
    return a;
  }
});
// Для нужд сериализации в формат JS0N интерпретировать множество как массив.
Set.prototype.toJSON = Set.prototype.toArray;

Оглавление книги


Генерация: 1.259. Запросов К БД/Cache: 3 / 0
поделиться
Вверх Вниз