javaScript中原型模式中的this向的是哪里?

夏友人的耕耘
  • 134
 function Person(age){
    this.age=age;
 }
 Person.prototype.getAge=function(){
    return this.age;
 }
 //调用函数
 var person=new Person(9);
 alert(person.getAge());//9

各位大神好,本人小白一枚。望能请教下,原型模式中的this指的是哪里(代码如上所述)?
按照我的理解,调用Person函数后,函数中的this应该指向的是调用它的对象new Person(9),而这个对象中拥有age属性,为该对象所特有;Person.prototype应该是另作为一个对象出现的,那么该对象就有自己的this来表示当前的对象Person.prototype.然而该this对象中没有age属性,两者的this应该不是同一个对象,那么调用后,就不应该显示为9.可实际确实显示为9???该如何理解?

高程中这么说,每个函数在被调的时都会自动取得两个特殊变量:this和arguments.内部函数在搜索这两个变量是,只会搜索到其活动对象为止;

回复
阅读 3.1k
5 个回答
✓ 已被采纳

我来试着解释一下

首先,

Person.prototype应该是另作为一个对象出现的

找不到理由反驳,它确实是一个对象。但你可能忽略了一点:prototype 是负责构建 instance(实例,也就是你 var 出来的 person)的 __proto__ 属性

那么该对象就有自己的this来表示当前的对象Person.prototype

我觉得影响你理解的关键问题出在这里。记住一句话就好:谁调用方法,this 就指向谁 (这样说能不能涵盖所有情况我不确定,但我一直这么理解的= =)。因此,你认为的 “该对象有自己的 this 来表示 Person.prototype” 是不确切的。.prototype 也不是个方法,根本就没有方法调用。后面你会看到,其实 新创建的对象 person 是继承自这个 Person.prototype,这样的关系。

另外,this 这个东西,只出现在执行上下文中,并不是 Object 的固有属性。一旦脱离了执行环境,谈 this 意义就不太大了。
证明这个很简单,你写一个函数调用,执行完了之后,你试试输出 this,如果你在浏览器 console 里运行,你应该只可能得到 Window。但如果你进入断点调试,你就可以输出每一个执行阶段的 this


理解了上面这些,咱们来看 new 这个关键字。先看这里:https://developer.mozilla.org...
重点帮你划好了:
clipboard.png

那么现在你应该就能理解,var person=new Person(9); 这行代码的结果就是,person 这个 Object,里面有了个 age 属性,而且这个属性的值为 9。


回到显示 9 的问题,现在你应该能理解了吧。person.getAge(),显然,getAge() 是一个方法,person 这个东西在调用他,因此,在 getAge() 这个方法的上下文(执行环境)里this 就是指代 person,因此这个时候函数返回 person.age,因此是 9

不知道这么说你明白了没。。有问题的话评论就好。

首先要明确一个非常非常关键的知识点,我们才能够慢慢解释this的指向,那就是
一个函数在被激活运行时,会创建该函数的执行上下文。
this的指向只会在执行上下文创建过程中确定。

因此,如果我们像普通函数一样直接调用声明的构造函数,构造函数中的this,仍然是指向全局的Window对象

function Person() {
    console.log(this); 
}

// 普通调用,this指向window
Person(); 

而使用new关键字来调用时,为什么会有所不同呢?《javascript高级编程》中有详细的说明。使用new时,经历了下面4个步骤。

  • 创建一个新的对象;

  • 将构造函数的作用域赋给新对象(因此,这里的this就指向了新的对象);

  • 执行构造函数中的代码;

  • 返回新对象。

因此,构造函数中的this指向在new Person(9)时被确定,它指向了创建的新对象,而这个新对象的引用在var person=new Person(9); 时被变量person接收,因此我们可以直接说构造函数中的this,指向了person。这个person,就是新的实例。

原型对象中的this,在person.getAge()执行时,才被确定。
毫无疑问,此时的this,也是指向了新的实例,而非指向原型对象。

从你的提问中可以看出,题主对于JavaScript的一些概念理解还有偏差,关于引用类型,关于执行上下文,关于原型等。所以这里安利一下自己的文章,最近正在回头做一个js基础知识的梳理与总结,欢迎关注,大家一起学习进步

http://www.jianshu.com/p/a6d3...

学习js,你要记住一点,理论上不存在所谓的对象的方法这个概念,一个对象的方法只是它的这个属性的值是对一个函数的引用,决定this的是这个函数对象被调用的情况,也就是所谓的上下文。详细内容我建议你看一本《You dont know js》中对这个问题的解释,非常清楚也很深入。

不管是什么this,都是根据上下文执行环境确定的。运行的时候才能确定最终的this指向。
你这个例子中原型上的this,是指向新创建的实例查找实例有没有age,结果是有就输出了。在实例没找到就会像原型链上找

宣传栏