(开放编辑以获得更好的问题标题 - 很难说出我在寻找什么)
你好,
我一直在使用原型,但最近发现需要在原型中使用命名空间来对相关功能进行分组。代码最简单的形式如下所示:
// Base grid functions.
Grid.prototype = {
init: function init() {
document.getElementById("output").innerHTML += "<br>" + this.id;
this.Rows.init();
this.Test.init();
document.getElementById("output").innerHTML += "<br><br>";
},
Test: {
init: function init() {
document.getElementById("output").innerHTML += "<br>" + this.id;
}
}
};
// Additional row-related and row utility functions.
Grid.prototype.Rows = {
init: function init() {
document.getElementById("output").innerHTML += "<br>" + this.id;
}
};
在我的Rows
“命名空间”中,我想维护上下文,this
以便开发人员可以调用函数gridInstance.Rows.get()
,例如,而不必每次都传递上下文(通过调用或应用)。
为此,我使用 LoDash 的_.bind
函数将每个新Grid
实例的上下文设置为每个与行相关的函数的上下文。
请注意,Test
“命名空间”纯粹是为了看看,当嵌套在Grid
原型中时,它是否会产生不同的结果。
var Grid = function Grid(id) {
var t = this;
// Assign an id to the control.
if (!id) {
// Assign a custom id if the control does not have one.
id = "grid-" + new Date().getTime();
}
t.id = id;
_.each(t.Rows, function (rowFn, key) {
t.Rows[key] = _.bind(rowFn, t);
});
_.each(t.Test, function (rowFn, key) {
t.Test[key] = _.bind(rowFn, t);
});
t.init();
};
这里有一个小提琴,显示输出:
x x x
y x x
z x x
我的问题是,为什么Rows
原型没有被实例化为新的(就像Grid.prototype
你每次调用时一样new Grid()
,我该如何解决这个问题?
额外的想法
我的想法是,Grid.prototype
作为任何新Grid
实例的蓝图,它将包含命名空间Rows
作为其中的一部分。
因此,在构造函数中,当我应用toGrid
的新上下文时,最初将是蓝图的副本,而不是仅属于该实例的引用。this
this.Rows
this.Rows
Grid.prototype.Rows
在Grid
构造函数中,我想我会修改this.Rows
,例如,绑定到的上下文this
,而不是原型本身。
发布答案
我的额外想法很愚蠢,因为我忘记了原型被继承自它的所有对象引用,而不是被用作对象实例的蓝图。
这里的小提琴说明了这一点。