【发布时间】:2016-07-26 13:52:24
【问题描述】:
我已经看过documentation,虽然作者提到了不同之处,但我还是不明白。
【问题讨论】:
标签: javascript dojo mixins
我已经看过documentation,虽然作者提到了不同之处,但我还是不明白。
【问题讨论】:
标签: javascript dojo mixins
我创建了两个小提琴来向您展示 declare.safeMixin 和 lang.mixin 是如何工作的不同案例。
从 Dojo 代码中提取的关于 declare.safeMixin 的文档:
此函数用于混合属性,如 lang.mixin 所做的,但它会跳过构造函数属性并装饰函数,如 declare() 所做的。
它旨在与由 declare 生成的类和对象一起使用。
与 dojo.safeMixin 混合的函数可以像普通方法一样使用 this.inherited()。
该函数用于实现由 declare() 生成的构造函数的 extend() 方法。
从 Dojo 代码中提取的关于 lang.mixin 的文档:
所有属性,包括函数(有时称为“方法”),不包括在 Object.prototype 中找到的任何非标准扩展,都从源复制/添加到目标。来源从左到右处理。
Javascript赋值运算符用于复制/添加每个属性;因此,默认情况下,mixin 执行所谓的“浅拷贝”,聚合类型通过引用进行复制/添加。
declare 创建的dojo 类:可以在here 找到工作示例。您需要打开控制台才能查看日志。
首先我们声明一个dojo类Person,然后创建这个类的两个实例:
var Person = declare(null, {
name: null,
message: "foo",
constructor: function(args) {
this.name = args.name;
},
speak: function() {
console.log(` ${this.name} says: '${this.message}'!`);
}
});
var rob = new Person({ name: "Rob" });
var peter = new Person({ name: "Peter" });
如果我们调用 speak 方法 rob 和 peter 会同时说出 foo。
现在我们用declare.safeMixin修改一个实例(rob)...
declare.safeMixin(rob, {
secondMessage: "bar",
speak: function() {
this.inherited(arguments);
console.log(` ${this.name} says: '${this.secondMessage}'!`);
}
});
...和另一个 (peter) 与 lang.mixin。
lang.mixin(peter, {
secondMessage: "bar",
speak: function() {
// this.inherited(arguments); // would cause an error
console.log(` ${this.name} says: '${this.secondMessage}'!`);
}
});
之后,Rob 会说两个词,因为我们使用了declare.safeMixin,这说明我们可以在我们的覆盖 speak 方法中使用this.inherited(arguments)。
Peter 只会说一个词而不是 Rob,因为我们使用了 lang.mixin,它完全覆盖我们之前的 speak 方法。
注意:您可以编写代码,使lang.mixin 也允许使用inherited(您需要在this.inherited 中明确命名要调用的方法) :
lang.mixin(peter, {
secondMessage: "bar",
speak: function() {
this.inherited('speak', arguments);
console.log(` ${this.name} says: '${this.secondMessage}'!`);
}
});
有关工作示例,请参阅 here。
可以在here 找到工作示例。您需要打开控制台才能查看日志。
首先我们声明两个对象,它们具有相同的属性foo。
var object= {
foo: "bar"
};
var anotherObject = {
foo: "bar"
};
然后我们再次修改两者。 object 实例与 declare.safeMixin ...
declare.safeMixin(object, {
baz: 123
}, {
baz: 1234
});
... 以及带有lang.mixin 的anotherObject 实例。
lang.mixin(anotherObject, {
baz: 123
}, {
baz: 1234
});
注意,我们在两个实例上混合,两个对象!现在如果我们尝试访问两个实例的baz 属性,我们将得到不同的结果。
object 实例 baz 属性将返回 123,因为 declare.safeMixin 仅支持在每个方法调用中混入一个 java 脚本对象。
anotherObject 实例 baz 属性将返回 1234,因为 lang.mixin 支持在每个方法调用中混入多个 java 脚本对象。这里很重要:最后一个获胜。
希望这能让事情变得更清楚。
【讨论】: