Подтвердить что ты не робот

Определение прототипа Javascript

Каковы функциональные различия между двумя прототипами Javascript и есть ли какие-либо преимущества для выбора одного из них?

Вариант 1:

Person.prototype.sayName = function(name) {
   alert(name);
}

Вариант 2:

Person.prototype = {
   sayName: function(name) {
      alert(name);
   }
}

Правильно ли я полагаю, что Вариант 2 приводит к обрыву определенных функций, которые неявно связаны с прототипом?

4b9b3361

Ответ 1

Правильно ли я полагаю, что Вариант 2 приводит к обрыву определенных функций, которые неявно связаны с прототипом?

Да, точно. Хотя единственным неявно связанным свойством является свойство constructor, которое вам редко нужно.

Каковы функциональные различия?

Вариант 1 просто расширяет существующий прототип. Если уже есть экземпляры Person, наследуемые от объекта-прототипа, они также смогут использовать метод sayName. С помощью опции 2 новый прототип будет использоваться только для объектов, которые создаются после перезаписи.

Есть ли какие-либо преимущества для выбора одного из них?

Теперь они должны быть самообучающимися. Вариант 1 (продление) считается более чистым и является обязательным, если вы модифицируете чужие/неизвестные/родные прототипы. Попытайтесь избежать варианта 2.

Если вам по-прежнему нравится синтаксис объектного литерала, вам следует использовать Object.assign, чтобы расширить существующий прототип:

Object.assign(Person.prototype, {
   sayName: function(name) {
      alert(name);
   }
});

Вам может понадобиться polyfill Object.assign для сред предварительного ES6. В качестве альтернативы $.extend или _.extend работают так же, как Что ж. Разумеется, ваша любимая библиотека поставляется с вспомогательной функцией для этого.

Ответ 2

Вторая перезаписывает person.prototype с объектом.

Первый метод:

Object.toString=function(){
  return "Object to string";
}
var Person = function(){
};
Person.toString=function(){
  return "Person to string";
}
Person.prototype.sayName=function(){}
console.log(Person.prototype.constructor.toString());// "Person to string"

Метод второй:

Object.toString=function(){
  return "Object to string";
}
var Person = function(){
};
Person.toString=function(){
  return "Person to string";
}
Person.prototype = {
  sayName:function(){}
}
console.log(Person.prototype.constructor.toString());// "Object to string"

Ответ 3

Первое хорошо для одной или двух дополнительных функций, но определение совершенно нового прототипа со многими функциями будет очень повторяющимся. С другой стороны, выполнение последнего уничтожит все существующие определения прототипа, как вы упомянули.

На практике я использовал первый, чтобы определить дополнительные функции в Array и Math и т.д., несколько похожие на категории в Objective-C. Последнее я использую как "определение класса".

Ответ 4

Любые существующие экземпляры конструктора будут продолжать указывать на старый объект-прототип. Любые новые созданные экземпляры указывают на новый объект-прототип.


Преимущества варианта 1 над вариантом 2 просто в том, что вам не нужно восстанавливать свойство конструктора, и вы сохраняете один уровень отступов, который огромен для меня.

Чтобы сохранить повторение, я просто присваиваю свойство локальной переменной:

var method = Person.prototype;

method.getAge = function() {
    return this.age;
};

method.getName = function() {
    return this.name;
};

Также существуют обычные варианты fn (jQuery) и p, которые еще короче method.

Ответ 5

Простыми словами разница в Person.prototype.sayName заключается в том, чтобы добавить функцию к prototype. просто добавив новые функции.

Во втором Person.prototype = {} здесь вы создаете новый цельный объект и назначаете его prototype. Таким образом, вы создаете новый объект или перезаписываете prototype новым объектом.

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

Второй метод хорош, если ваши объекты приложения совместно используют некоторые объекты (или группу функций, таких как @isaach, упомянутых в Math functions).