【发布时间】:2011-02-17 13:07:54
【问题描述】:
除了eval(`o = new ${className}(${args.join(", ")})`),还有其他方法可以使用可变参数列表来实例化对象吗?
例如:var foo = instantiate(className, [arg1, arg2, ...])
【问题讨论】:
标签: javascript
除了eval(`o = new ${className}(${args.join(", ")})`),还有其他方法可以使用可变参数列表来实例化对象吗?
例如:var foo = instantiate(className, [arg1, arg2, ...])
【问题讨论】:
标签: javascript
你可以用这样的变量参数列表实例化一个对象:
function instantiate(className, args) {
var o, f, c;
c = window[className]; // get reference to class constructor function
f = function(){}; // dummy function
f.prototype = c.prototype; // reference same prototype
o = new f(); // instantiate dummy function to copy prototype properties
c.apply(o, args); // call class constructor, supplying new object as context
o.constructor = c; // assign correct constructor (not f)
return o;
}
旁注:您可能希望传递对类构造函数的直接引用:
var foo = instantiate(Array, [arg1, arg2, ...]);
// Instead of:
var foo = instantiate("Array", [arg1, arg2, ...]);
...这使得它与非全局函数兼容。
【讨论】:
window[className] 对我来说是未定义的(是的,三次检查我的班级名称)。
在 ES5 中使用 Object.create():
function instantiate(constructor, args) {
var instance = Object.create(constructor.prototype);
constructor.apply(instance, args);
return instance;
}
在 ES6 中使用 spread operator:
var foo = new constructor(...args);
【讨论】:
好吧,您总是可以按照以下方式进行操作。添加到 Dino 原型的任何内容都可以在实例化对象之间共享。与普通构造函数模式的不同之处在于,实例化对象不必具有完全相同的私有属性集。可以为它们中的每一个动态设置它们。
function Dino(a,b){
for(i = 0; i< a.length; i++) this[a[i]] = b[i];
}
var props = ["foo", "bar"],
values = [42, 37],
obj = new Dino(props,values);
console.log(obj);
【讨论】: