Курсовая работа (проект) Курстық жұмыс (жоба) тақырыбы Тема курсовой работы (проекта) Разработка сайта об автомобилях с помощью JavaScript


Описание функционала интернет-магазина



бет5/7
Дата30.04.2024
өлшемі65.5 Kb.
#500219
түріКурсовая
1   2   3   4   5   6   7
Лесбек Әділет курсавой

2.2 Описание функционала интернет-магазина

Помните обсуждение .constructorproperty ранее и тот факт, что оно выглядит как .constructor === Значение Foo true означает, что существует фактическое свойство .constructor, указывающее на Foo? Это не верно.


Это просто печальный беспорядок. Фактически, ссылка .constructor также передается в Foo.prototype, который по умолчанию имеет .constructor, указывающий на Foo.
Кажется очень удобным, что объект, «созданный» Foow, имеет доступ к свойству .constructorproperty, которое указывает на Foo. Но это не более чем ложное чувство безопасности. Это случайный случай делегирования по умолчанию .constructor в Foovia. Есть несколько причин, по которым надоедливое предположение о том, что .constructor означает «построенный», может вас укусить.
Во-первых, свойство .constructorproperty в Foo.prototype присутствует только в объекте, созданном, когда функция Foothe объявлена ​​по умолчанию. Если вы создадите новый объект и замените ссылку на объект .prototype функции по умолчанию, новый объект не будет магическим образом наследовать .constructor по умолчанию.
Учитывать:
функция Foo() { / .. / }
Foo.prototype = { / .. / }; // создаем новый объект-прототип
вар a1 = новый Foo(); a1.constructor === Фу; // ЛОЖЬ!
a1.constructor === Объект; // настоящий!
Объект(..) не «создал» a1, не так ли? Кажется, Foo() «создает» его. Многие разработчики думают, что Foo() создает конструктор, но все ломается в том, что вы думаете, что «конструктор» означает «созданный», потому что по этой логике a1.constructor должен быть Foo, но это не так. !
Что происходит? У a1 нет свойства .constructor, поэтому он передает свою строку в Foo.prototype. Но у этого объекта также нет .constructor (как у объекта Foo.prototype по умолчанию!), поэтому он продолжает делегировать тип Object.pro на вершине цепочки делегирования. Этот объект действительно существует
Конечно, вы можете переназначить .constructor объекту Foo.prototype, но это потребует ручной работы, особенно если вы хотите соответствовать нативному поведению и сделать его неперечисляемым (см. главу 3).
Например:
функция Foo() { / .. / }
Foo.prototype = { / .. / }; // создаем новый объект-прототип
// Отсутствующий `.constructor` должен быть правильно "исправлен".
// Свойство нового объекта, которое служит `Foo.prototype`. // См. главу 3 для `defineProperty(..)`. Object.defineProperty( Foo.prototype, "конструктор", {
перечисляемый: ложь, записываемый: правда, настраиваемый: правда,
value: Foo // `.constructor` указывает на `Foo` } );
Исправление .constructor требует много ручной работы. Более того, учитывая ошибочное представление о том, что все, что мы на самом деле делаем, это вечное «конструктор» означает «построенный». Это дорогая иллюзия.
Проблема в том, что .constructor объекта по умолчанию произвольно указывает на функцию, имеющую обратную ссылку на объект — ссылку, которую он вызывает .prototype. Слова «конструктор» и «прототип» имеют только значение по умолчанию, которое может или не может быть выполнено позже. Лучше всего помнить, что «построено не значит построено».
Конструктор не является магическим неизменяемым свойством. Оно нечисловое (см. предыдущий фрагмент), но его значение доступно для записи (изменяемо), и вы можете добавить или перезаписать (намеренно или случайно) свойство конструктора имени для любого объекта в любой последовательности [[Тип прототипа]]. , с любым значением, которое вы считаете подходящим.
В зависимости от того, как алгоритм [[Get]] проходит цепочку [[Proto type]], ссылка на свойство .constructor, найденная где угодно, может быть решена совершенно иначе, чем вы ожидаете.
Результат? Некоторым произвольным ссылкам на свойства объекта, таким как конструктор a1.con, нельзя доверять как ссылку на функцию по умолчанию. Более того, как мы вскоре увидим, просто опустив его, конструктор a1.constructor может даже открыть удивительное и неосязаемое место.
a1.constructoris очень ненадежен и является ненадежной ссылкой в ​​вашем коде. Как правило, таких ссылок следует избегать, когда это возможно.
Мы видели некоторые приближения к механике классов, которые обычно не работают в программах на JavaScript. Но классы JavaScript были бы гораздо более пустыми, если бы у нас не было приближения «наследования».
Фактически, мы увидели в работе механизм, обычно называемый прототипическим наследованием, с помощью которого мы можем «наследовать» от типа Foo.pro и, таким образом, получать доступ к функции myName(). Но мы традиционно думаем о наследовании как об отношениях между двумя классами, а не между классом и экземпляром:
Вспомните это изображение ранее, оно напоминает концепцию наследования родительских и дочерних классов не только от объекта a1 к объекту Foo.prototype, но также от Bar.prototype к Foo.prototype. Аналогично, конечно, за исключением направления стрелок, которое указывает на то, что это репрезентативные ссылки, а не действия копирования.
Вот типичный код в стиле «прототипа», создающий такие ссылки:
функция Foo(имя) { this.name = name;
}
Foo.prototype.myName = function() { return this.name;
};
function Bar(name, label) { Foo.call(this, name); this.label = метка;
}
// здесь мы создаем новый `Bar.prototype` // привязанный к `Foo.prototype`
Bar.prototype = Object.create( Foo.prototype);
// Будь осторожен! `Bar.prototype.constructor` теперь удален, // и если у вас есть привычка // полагаться на такие свойства, возможно, вам придется «исправить» его вручную!
Bar.prototype.myLabel = function() { return this.label;
};
var a = new Bar( "a", "obj a");
а.моеИмя(); // "а" a.myLabel(); // "объект а"
См. главу 2, чтобы понять, почему это не относится к предыдущему фрагменту кода.
Важная часть — Bar.prototype = Object.create (Foo.pro totype). Вызов Object.create(..) создает «новый» объект из воздуха и привязывает подстроку этого нового объекта к указанному вами объекту (в данном случае Foo.prototype).
Другими словами, в этой строке говорится: «Создайте новый объект-прототип точки Bar, связанный с прототипом точки Foo».
Когда объявлена ​​функция Bar() { .. }, Bar, как и любая другая функция, имеет ссылку .prototype на свой объект по умолчанию. Но этот объект не привязан, как Foo.prototype, который нам нужен. Таким образом, мы фактически выбрасываем исходный объект, который был привязан неправильно, и создаем новый объект, привязанный так, как мы хотим.
Распространенным заблуждением здесь является то, что любой из следующих методов будет работать, но не так, как вы ожидаете:
// не работает так, как вы хотите! Bar.prototype = Foo.prototype;
// работает как хотите, но вместе
// побочные эффекты, которые вам, вероятно, не нужны :( Bar.prototype = new Foo();
Bar.prototype = Foo.prototype не создает новый объект для связанного Bar.prototype. Он создает ссылку Bar.prototype на другой Foo.prototype, которая эффективно связывает Bar непосредственно с тем же объектом, на который ссылается Foo: Foo.prototype. Это означает, что когда вы начинаете назначать что-то вроде Bar.prototype.myLabel = ... , вы изменяете не отдельный объект, а сам общий объект Foo.prototype, который влияет на любые объекты, к которым привязан Foo.prototype. Это определенно не то, что вы хотите. Если это то, что вам нужно, тогда вам вообще не нужен Bar, просто используйте Foo и сохраняйте свой код простым.



Достарыңызбен бөлісу:
1   2   3   4   5   6   7




©dereksiz.org 2024
әкімшілігінің қараңыз

    Басты бет