欢迎您访问程序员文章站本站旨在为大家提供分享程序员计算机编程知识!
您现在的位置是: 首页  >  IT编程

原型链方法使用实例讲解

程序员文章站 2022-08-10 14:22:45
有下列例子 function Foo() { } Foo.prototype.getName = function () { alert(3); }; var foo...

有下列例子

function Foo() {

}

Foo.prototype.getName = function () {

alert(3);

};

var foo = new Foo();

foo.getName();// 3;

Foo.getName();// Foo.getName is not a function

问题:

1、var foo = new Foo();这一句语法到底做了那几件事?

2、为什么在Foos上定义的原型方法,使用Foo调用不出来?

回答:

1、“

var foo = new Foo();

”在这个语句中我们声明了一个foo对象,用“Foo()”这一个构造函数来初始化foo对象,赋予初始值。这个过程被称之为对象的实例化。

也就是由抽象到具体的过程。

Foo在这个例子中被创建为一个构造函数,这个语句与“ var foo = new Array ();”类似,Array也是构造函数。可以理解为,

创建了一个Foo的类,在这个类里面实例了一个对象foo,它属于Foo类,通过原型链可以使用Foo原型链上的方法,也是一种常用的创建对象的方法。

这个方法看似像一个函数,但又有些不太一样。比如函数名一般都小写。如果学过其他面向对象的语言就会知道,这是类的写法(此处不多分析,非强制,但这么写有助于区分构造函数和

普通函数)。这种方法是构造函数创建对象的写法,通过构造函数创建对象,必须使用new 运算符。

构造函数可以创建对象执行的过程:

1)当使用了构造函数,并且new 构造函数(),那么就后台执行了new Object();

2)将构造函数的作用域给新对象,(即new Object()创建出的对象),而函数体内的this 就

代表new Object()出来的对象。

3)执行构造函数内的代码;

4)返回新对象(后台直接返回)。

注:

1)构造函数和普通函数的唯一区别,就是他们调用的方式不同。只不过,构造函数也是函数,必须用new 运算符来调用,否则就是普通函数。

2)this就是代表当前作用域对象的引用。如果在全局范围this 就代表window 对象,如果在构造函数体内,就代表当前的构造函数所声明的对象。

这种方法解决了函数识别问题,但消耗内存问题没有解决。同时又带来了一个新的问题,全局中的this 在对象调用的时候是Box 本身,而当作普通函数调用的时候,

this 又代表window。即this作用域的问题。

2、为什么在Foo上定义的原型方法,使用Foo调用不出来?

一个对象上的方法,可以是方法自身的方法,也可以是原型链上的方法。一般情况下的查找方式是先查找自身有没有getName方法,查找代码如下

Foo.getName();//此时查找的是Foo本身的方法,而此时Foo本身并未定义方法,所以沿着原型链往上查找。先找__proto__,发现指向Function.prototype。

在这依然没有找到,往下走寻找Function.prototype.__proto__,发现指向Object.prototype,再往后找到Oject.prototype.__proto__。沿着prototype原型

链寻找找不到这个方法后返回undefined。

Foo.prototype.getName();// 返回3,此时查找的是原型链上的方法,找到后按找方法返回3

foo.getName();// 此时先在foo对象本身的方法上查找,没有找到,然后到__proto__,查询到Foo.prototype并在上面发现getName方法。返回3。