2009-09-03 97 views
12

我刚刚开始阅读道格拉斯克罗克福德的“Javascript良好部分”,他在那里解释增强基本类型。Javascript增加基本类型(原型继承)的疑问

Function.prototype.addMethod=function(name,func) { 
    this.prototype[name]=func; 
    return this; 
}; 

这样做之后的那一刻,addMethod可用像字符串所有的基本对象,等。这使我感到困惑

[1]为什么会出现这种情况当我还没有添加到Object.prototype

[2]为什么添加方法Function.prototype的被反映在所有基本对象?

我很新的JavaScript和原型继承。所以我不知道我的问题是否愚蠢?

+0

不,这是JavaScript的执行原型继承是愚蠢的。其奇怪的使用函数作为构造函数样式给你没有原型的潜在优势,但仍然与大多数程序员所理解的基于类的继承无异。很高兴能够准确理解JavaScript原型正在做什么,但不要期望突然明白为什么该模型有意义。因为它不。 – bobince 2009-09-03 15:16:44

回答

16

他大概的意思正是这样做之后,addMethod成为可用于所有基本 对象 对象类型像字符串,数字等,这是因为String对象是一个函数(但字符串创建的对象都没有)。

例如,鉴于

var s = ''; 

你可以做

String.addMethod(...); 

但不

s.addMethod(...); 

JavaScript的类型系统的简要介绍到这里:

JavaScript并不有正常的课程概念。相反,通过将任何函数转换为构造函数,可以通过在调用时将new关键字放在它前面来达到相同的效果。

E.g:给予

function MyFunction(x) { this.myX = x; } 

如果你调用它像

var myObj = new MyFunction(10); 

它会创建一个名为MyObj中的对象。这个对象将有一个名为myX的成员变量。该函数myFunction是考虑对象的构造函数(并存储在“构造”特性

(奖金的问题:如果你调用该函数上面没有新的关键字,即var x = MyFunction(10)会发生什么,答案很可能惊奇任何明智的人)

现在您已经看到了如何将任意函数转换为构造函数。内建对象完全相同,字符串对象由函数String创建,数字由函数创建编号等

就像是由函数创建的那些内置的对象,每个对象的这些功能也是通过“功能”功能创建(亚克西!)。

现在到原型。

在上面的例子中

,如果你的地方写

MyFunction.prototype.someNewMethod = function() {} 

由MyFunction的构造函数创建的所有对象/功能会出现有所谓someNewMethod一个额外的成员函数。你可以用原型做很多其他有趣的事情,比如替换原型,或者替换原型的原型,但我不是这方面的专家。

+0

根据'this.prototype [name]'判断,我认为你完全正确。 – 2009-09-03 11:29:48

+1

你能解释一下吗?找到困难的概念。 – 2009-09-03 12:14:14

+0

@erikkallen 如何是字符串对象类型(或任何其他基本对象类型)的函数?它是否像String对象有一个构造函数是一个Function对象?请多解释一下! – sriramptr 2009-09-03 16:22:20

1

在面向对象的JavaScript,功能可以作为一个类&构造函数。所以,如果你的类被命名为MyObject,你可以做到以下几点:

// create a class/constructor 
function MyObject() { 
    // ... 
} 

// add a static method to the MyObject class 
MyObject.someFunction = function() { 
    // ... 
} 

// add an instance method to the MyObject Class 
MyObject.prototype.someFunction = function() { 
    // ... 
} 

在您的例子中,addMethod加入作为实例方法的功能类,这意味着它是提供给函数的所有实例。 MyObject函数/类/构造函数是Function的一个实例,因此您可以在其上调用addMethod。这适用于大多数任何对象类型,但不适用于IE和其他浏览器中的HTMLElements。

1
  1. JavaScript中的函数是对象。所有对象都有一个到Object.prototype的隐藏链接 。因此,对于第一个声明:

    > `Function.prototype.addMethod=function(name,func) {} 
    

    您已经声明链接到其自身连接到Object.prototype中Function.prototype的功能。

  2. 对于第二部分的只是一个任务,你要设置的名称值对的Object.prototype中,将返回add方法的所有字符串,数字对象,因为它是所有在原型声明。