2012-04-23 3 views
11

Я бил головой об этом в течение последних двух дней. По какой-то причине основой являются данные родительского экземпляра через унаследованные дочерние модели. Вот пример:Backbone.js: Наследование модели вызывает общие данные

var Base = Backbone.Model.extend({ 

    index : [] 

}); 

var Group = Base.extend({ 

    initialize : function() { 
    this.index.push('from group'); 
    } 

}); 


var User = Base.extend({ 

    initialize : function() { 
    this.index.push('from user'); 
    } 

}); 


var user = new User(); 
console.log(user.index); // ['from user'] 


var group = new Group(); 
console.log(group.index) // ['from user', 'from group'] 

Что я ищу это:

console.log(user.index); // ['from user'] 
console.log(group.index) // ['from group'] 

Любые идеи?

Спасибо! Мэтт

ответ

14

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

var Base = Backbone.Model.extend({ 

initialize: function() { 
    this.index = []; 
} 


}); 
+0

Спасибо за ваш ответ. Я действительно надеялся, что 'extend()' будет избегать этой проблемы путем клонирования объектов/массивов. Похоже, что эту практику определения массивов и объектов в родительском классе следует избегать, поскольку это может привести к непреднамеренным последствиям. – Matt

+3

Есть причины для определения объектов или массивов в классах, подобных этому, но вы намерены использовать индекс в качестве переменной экземпляра, чтобы он был уникальным для каждого экземпляра, а не общим для всех экземпляров, таких как переменные класса. Если вы хотите переменные экземпляра, то да, вы не должны определять их в объекте, переданном для расширения, но если вы хотите переменную класса, то да, это прекрасно. Совершенно точно определить переменные экземпляра в конструкторе родителя, как показал Skylar. – chubbsondubs

6

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

Для того, чтобы это была переменная экземпляра, вам необходимо создать экземпляр в конструкторе для Base и дать каждому подклассу этот конструктор из их соответствующих конструкторов. Нравится:

var Base = Backbone.Model.extend({ 
    initialize: function() { 
     this.index = []; 
    } 
}); 

var User = Base.extend({ 
    initialize: function() { 
     Base.prototype.initialize.call(this); 
     this.index.push('User'); 
    } 
}); 

// repeat it for group. 
+0

Спасибо за ваш ответ. Это еще один способ решить проблему. – Matt

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