2013-03-23 2 views
0

У меня есть объект javascript с несколькими методами. Однако я замечаю некоторую несогласованность в том, как определяются методы.Несоответствие определения метода JavaScript

Здесь объект:

function MenuObject(containerId, skin) { 

    this.id = containerId; 
    this.something = something2; 
    . 
    . 
    . 
    this.anotherThing = anotherThing2;  

    this.setSkin = function(skin) { //We have a function here 

     //body... 
    { 


} 


MenuObject.prototype.getTopLevelPolygon = function() //Another function. 
{ 
    var p = this.something3; 

    //Method body goes here... 
} 

Некоторые из функций, которые определены как this.functionName = функции(), другие, как MenuObject.prototype.functionName = функции()

Мне просто интересно, почему не все функции, которые принадлежат элементу MenuObject, определенные как MenuObject.prototype.functionName = function()?

+1

Так что * реальный вопрос: «Почему методы добавлены в .prototype?» или, может быть, «Какова собственность« прототипа »? или .. Подсказка: найдите «прототип javascript». – 2013-03-23 00:36:56

ответ

2

Если вы не используете переменные частного экземпляра, то, как правило, более эффективно определять методы с использованием прототипа, поскольку они назначаются новому объекту одним махом внутренности javascript (через прототип), а не назначаются индивидуально в то время в вашем собственном коде.

И хорошая практика кодирования говорит, что вам не следует использовать сочетание методов, если для этого не существует конкретной причины (и этот код не указывает на какую-либо конкретную причину использования микса).

Есть причины для назначения методов в конструкторе, если вы хотите, чтобы они имели доступ к частной переменной экземпляра:

function MenuObject(containerId, skin) { 

    var myPrivateVariable = 0; 

    this.setSkin = function(skin) { 
     // method can access myPrivateVariable here, 
     // but a method put on the prototype cannot access it 
    } 
} 

Вы можете прочитать больше о частных переменных экземпляра здесь: http://javascript.crockford.com/private.html

+0

@JoroSeksa - см. Мое последнее редактирование. Он имеет переменную частного экземпляра. См. Здесь для более полной записи: http://javascript.crockford.com/private.html – jfriend00

1

Ну, короткий ответ заключается в том, что элементы, назначенные с помощью this.functionName = function() в конструкторе, создаются по требованию, а созданные с помощью prototype больше похожи на статические функции, поскольку они существуют вне экземпляра «функции» и строятся при выполнении программы, в отличие от экземпляра. Несоответствия либо преднамеренные, либо продукт программирования младшего уровня (возможно, ранее).

Edit:

Кстати, есть даже больше, чем это, но детали идут дальше и дальше, одна вещь просто пришла на ум, это также позволяет иметь «частные» функции внутри «класс», если вы позволите мне называть это так. Кроме того, можно определить прототип объекта таким образом:

SomeFunction.prototype = { 
    SomeFn1:function(){}, 
    SomeFn2:function(){}, 
    SomeFn3:function(){} // etc etc 
}; 
1

Разница заключается в том, когда вы хотите добавить общественные функции объекта.

Метод this.functionName = function() требует определения всех ваших функций объекта во время объявления объекта function MenuObject(containerId, skin) { ... };.

Метод MenuObject.prototype.functionName = function() позволяет добавить дополнительные функции объекта после объявив объект ранее. Так что вроде как добавить плагины или увеличить объект для разных ситуаций.

1

методы Определение внутри конструктора (this.method = fun ..) можно использовать «частные» данные с помощью закрытия. Кроме того, методы внутри конструктора создаются каждый раз при вызове конструктора.Если вы не используете «новый» при вызове конструктора, «это» обычно прикрепляется к глобальному объекту окна, и поэтому может привести к очень запутывающим и непонятым ошибкам.

Определение методов вне конструктора (MenuObj.prototype.method = fun ..) может быть перезаписано позже в коде в любое время, тогда как определение внутри конструктора всегда имеет приоритет и не может быть перезаписано модификациями прототипов , Редактирование прототипа влияет на цепочку прототипов и может привести к очень запутывающим и непонятным ошибкам.

Я предлагаю прочитать книги Дугласа Крокфорда или перейти на его сайт http://www.crockford.com/ и посмотреть видео и эссе на JavaScript.

Смежные вопросы