这两个代码有什么区别,我应该使用哪一个?
function Test() {}
Test.method = function() {};
使用Prototype:
function Test() {}
Test.prototype.method = function() {};
答案 0 :(得分:5)
第一种情况:静态方法。
function Test() {}
Test.method = function () { alert(1); };
var t = new Test;
Test.method(); // alerts "1"
t.method(); // TypeError: Object #<Test> has no method 'method'
第二种情况:实例方法。
function Test() {}
Test.prototype.method = function () { alert(1); };
var t1 = new Test;
var t2 = new Test;
t1.method(); // alerts "1"
t2.method(); // alerts "1"
Test.method(); // TypeError: Object function Test() {} has no method 'method'
答案 1 :(得分:1)
第一个示例仅将函数分配给名为Test
的{{1}}的新属性。关于它没有什么特别的或神奇的(我的意思是,语言不会对它做任何有趣的事情)。您可以将其称为 static 方法,因为它在所有实例中共享,但它实际上只是一个普通的属性。 (函数是对象,对象具有属性。)
在第二种情况下,method
的{{1}}添加了一种新方法,该方法可供Test
的所有实例使用。此是特殊行为。 JavaScript中的每个对象都有一个指向另一个对象的内部链接,称为原型。此链接是使用创建对象的构造函数的prototype
建立的,因此Test
创建的任何实例都将在其原型链中具有新属性。
例如:
prototype
可是:
Test
答案 2 :(得分:0)
原型方法在Test
的所有实例之间共享。
答案 3 :(得分:0)
function Test() {}
Test.method = function() {};
function Test() {}
Test.prototype.method = function() {};
假设您创建了一个Test实例:
t = new Test()
在调用方法时:
t.method()
JavaScript将首先在Test中查看,例如,下面将识别3个属性和方法:
function Test() {} {
this.a = "hello";
this.b = "world";
this.c = function() { alert( this.a + this.b) }
}
然后第二,查找将在原型上完成:
Test.prototype.method = function() { console.log('prototype defined method') }
在JavaScript中,以下内容不会注册到实例t
,而是注册Test
:
Test.method = function() { console.log('something unsual') };
因此
Test.method() // works
t.method() // no works
答案 4 :(得分:0)
差异可以追溯到原型链的工作原理。如果您创建Test实例,那么他们将能够访问原型上定义的方法。
第一个代码,只是在构造函数上添加一个“静态”方法;你将无法访问这种方法:
var testInst = new Test();
testInst.method() // Error Undefined is not a function
调用该方法的唯一方法是通过构造函数引用,即
Test.method();
正如我所提到的,如果将方法添加到构造函数的原型中,则上述操作是可行的。
答案 5 :(得分:0)
如果在原型中定义方法,则任何实例都可以使用该方法。如果将方法定义为原始对象的一部分,则允许您以可合理地称为静态方法的方式使用该方法。
例如:
Array.isArray( [] ) //true
[].isArray() //throws a TypeError
第二个示例抛出TypeError
,因为isArray()
不在Array.prototype
中(请记住,实例仅访问在该实例中定义的方法,或者在该实例的prototype
中或__proto__
链)。
简而言之:
*原始对象中定义的方法可以由该对象访问,但不能访问该对象的实例
*原始对象的原型中定义的方法可以由原始对象的任何实例访问。