使用Object.create()复制构造函数和new
Replicating constructors and new with Object.create()
根据我对OOP javascript的有限经验,处理具有不同属性但方法相同的多个对象的常见方法是使用如下构造函数:
function Animal ( type ) {
this.type = type
};
Animal.prototype.sayHello = function () {
return 'Hi, I am a ' + this.type
};
var goat = new Animal( 'Goat' );
我在这里的理解是goat
将继承/引用Animal
的功能。
我假设我可以用以下对象字面概念复制上面的内容:
var Animal = {
type : '',
sayHello : function () {
return 'Hi, I am a ' + this.type
}
}
var goat = Object.create( Animal );
goat.type = 'Goat';
对Animal
的继承在这里丢失了吗?还是Goat
仍在引用方法的Animal
?
我想知道使用Object.create()
而不是new
来复制构造函数/类是否有任何问题。是否存在性能偏移或继续使用new
的任何原因?
任何建议都将不胜感激,如果需要澄清,我很乐意补充这个问题。
更新的对象创建
var Animal = {
sayHello : function () {
return 'Hi, I am a ' + this.type
}
}
var goat = Object.create( Animal, { 'type' : { value: 'goat' } } );
处理具有不同属性但方法相同的多个对象的常见方法是使用构造函数。。。
是的,另一种常见的方式是(正如您所看到的)Object.create
。
我在这里的理解是
goat
将继承/引用Animal
的功能。
不完全是。在new Animal
表达式中,goat
被分配由Animal.prototype
引用的对象作为其底层原型。没有到Animal
的直接连接,只有到Animal.prototype
的连接。(在正常情况下,Animal.prototype
通过其constructor
属性引用回Animal
,尽管如果有人将新对象分配给Animal.prototype
,则该链接可能会断开。)
对
Animal
的继承在这里丢失了吗?还是Goat
仍在引用方法的Animal
?
在您的非构造函数示例中,goat
将Animal
作为其底层原型,因此对于在goat
上找不到的任何属性,JavaScript引擎将查看Animal
,看看it是否具有它。在您的示例中,这意味着goat
使用的是Animal
中的sayHello
,而不是type
,因为goat
有自己的type
。
大致相当于:
function Animal ( type ) {
this.type = type
};
Animal.prototype.sayHello = function () {
return 'Hi, I am a ' + this.type
};
var goat = new Animal( 'Goat' );
使用Object.create
设置原型看起来是这样的:
var animalPrototype = {
sayHello: function () {
return 'Hi, I am a ' + this.type
}
};
function createAnimal(type) {
var rv = Object.create(animalPrototype);
rv.type = type;
return rv;
};
var goat = createAnimal( 'Goat' );
回复您的评论:
在
createAnimal
中包含animalPrototype
,然后调用Object.create(this.animalPrototype)
,会有什么问题吗?
如果你的意思是:
function createAnimal(type) {
var animalPrototype = { // Issue #1
sayHello: function () {
return 'Hi, I am a ' + this.type
}
};
var rv = Object.create(this.animalPrototype); // Issue #2
rv.type = type;
return rv;
};
var goat = createAnimal( 'Goat' );
是的,有两个问题:
- 您需要为每次对
createAnimal
的调用创建一个新的animalPrototype
,这会破坏目的,以及2。调用createAnimal
中的this
将是全局对象(宽松模式)或undefined
(严格模式),因此this.animalPrototype
可能不是您想要的表达式
你可以这样做:
function createAnimal(type) {
var rv = Object.create(createAnimal.proto);
rv.type = type;
return rv;
};
createAnimal.proto = {
sayHello: function () {
return 'Hi, I am a ' + this.type
}
};
var goat = createAnimal( 'Goat' );
当然,这可能会让人感到困惑,因为它看起来很像构造函数。
- ES6构造函数返回基类的实例
- 使用Google Visualization动态调用构造函数
- javascript中对象构造函数中的var属性与this.properties
- 理解typescript中的构造函数接口
- 为什么构造函数不是构造函数
- 断言使用new执行构造函数时抛出错误
- 如何模拟像 new Date() 这样的构造函数
- jshint 和 Function() gets:调用构造函数时缺少“new”前缀
- 带有和不带 new 运算符的 JavaScript 构造函数
- 使用Object.create()复制构造函数和new
- 当调用返回相同对象的函数时,无论是否作为构造函数调用,我都应该使用“new”吗
- JS - 使用“new”和将对象作为上下文传递给构造函数有什么区别
- 如何从Javascript中使用new调用的构造函数返回null
- 为什么函数在构造函数中声明时不使用new关键字
- 如果构造函数返回new Func()会发生什么?
- 当像new(Date)这样编写时,如何将参数传递给构造函数
- TypeError: & # 39;未定义# 39;不是构造函数(求'new JdRes())
- var platform=new PlatformJS给出构造函数错误
- return和new关键字构造函数模式的区别是什么?
- Javascript "文件"and "new File"构造函数