我有一个用 JSON 定义的现有对象数组。对象显然属于 Object 类型。如何将它们与自定义对象类型相关联以赋予它们特定功能?
5 回答
在所有浏览器中都可以使用的方式是使用您想要的属性和方法来扩充数组中的每个项目,或者将对象传递给构造函数并基于旧对象的属性和方法创建一个新对象。
或者,如果您不关心 IE:
var obj = {
name : "Jeremy"
};
function CustomType() {
this.name = this.name || "someValue";
this.greeting = "Hi";
}
CustomType.prototype.sayHi = function() {
alert(this.greeting + ", " + this.name);
};
obj.__proto__ = CustomType.prototype;
obj.constructor.call(obj);
obj.sayHi();
我不相信有任何方法可以在创建对象后更改它的类型。幸运的是,您可能实际上不需要更改对象的类——您可能会对为对象提供一些新方法和其他功能感到满意。(唯一真正的区别是如果您更改了类会发生什么,并且大多数人在代码运行时不会更改类。)
我会为你举一个例子。首先,我将创建一个简单的对象来表示您拥有的 JSON 对象:
var myobj = new Object()
myobj.name = "Fred"
然后我将创建一些您希望能够分配给的类myobj
:
function Speaker() {
this.speak = function() {
window.alert("Hello, " + this.name);
}
}
这个新Speaker
类有一些有用的功能:它可以使用方法speak()
输出有用的信息:
var s = new Speaker()
s.name = "Sally"
s.speak()
执行它给了我消息“你好,莎莉”。不幸的是,您不希望新对象(如s
)具有此功能,而是希望现有对象(myobj
)拥有它。这是你如何做到的:
myobj.speak = s.speak
现在当我执行这个:
myobj.speak()
我看到消息“你好,弗雷德”。
总结一下:创建一个做你想做的事情的对象。将所有方法(和任何辅助变量)复制到新对象中。除了一些不寻常的继承用途外,这将使您的新对象按预期运行。
如果你不需要构造函数,你可以这样做:
Object.assign(new CustomType, {});
如果你想对它们使用特定的方法,你可以使用 apply/call。
或者您可以复制自定义对象的方法。
function Object1() {
this.aValue = "10";
}
function CustomObject() {
this.customValue = "6";
}
function convertToCustom(obj) {
var custom = new CustomObject();
for( var key in obj ) {
custom[key] = obj[key];
}
return custom;
}
var obj = new Object1();
var custom = convertToCustom(obj);
console.log(custom.customValue); // <- 6
console.log(custom.aValue); // <- 10
作为对 Jeremy 的回答的补充,您可以使用 Object.create 而不是直接使用proto。您还需要一个“扩展”功能。
所以,以 Jeremy 的例子,你可以有这样的东西:
var obj = {
name : "Jeremy"
};
function CustomType() {
}
CustomType.prototype.init = function(){
this.name = this.name || "someValue";
this.greeting = "Hi";
return this; //let's make it fluent
}
CustomType.prototype.sayHi = function() {
console.log(this.greeting + ", " + this.name);
};
function extend(obj, props) {
for(prop in props) {
if(props.hasOwnProperty(prop)) {
obj[prop] = props[prop];
}
}
return obj; //let's make it fluent
}
obj = extend(Object.create(CustomType.prototype), obj).init();
obj.sayHi();