执行环境。以及与之相对应的变量对象。寻找变量时,是通过变量对象组成的作用域链来寻找的。
this引用的是函数执行的环境对象。即,在全局环境下的代码,this将指向window对象。
new操作符,通过新建一个对象,然后将构造函数的作用于赋给该对象(所以构造函数中通过this定义的属性最终成为了实例的属性)
闭包:创建函数时,总会创建一个预先包含当前该函数所在执行环境的的作用域链,所以,当该函数返回后(即该函数被引用后),创建该函数时,它所在的执行环境的活动对象,会被那个作用域链锁引用,从而一直保存在内存中,达到闭包的效果。
如果想要在闭包中调用this,因为闭包返回的函数之后不知道在哪里被调用,所以this并不总是想要的结果,所以可以通过在该函数的执行环境中(外层)将另外一个变量指向this,如var that = this.而后则可通过that调用当前的this,因为that被保存在当前执行环境的活动对象中,可以像其他的上层函数的私有变量一样被调用。
函数原型:在创建函数时,总会为它创建一个prototype的属性,即,函数原型。假若该函数为一个构造函数,则它创建的实例中会包含一个指针,__proto__,来指向构造函数的prototype。而javascript中的继承,常用的方式的一种就是,通过将子类构造函数的prototype等于父类的实例,从而使得子类构造函数的prototype中存在一个指针去指向父类构造函数的原型。而当并未进行任何此类操作的时候,函数的原型中仍然会包含这样一个指针,而这个指针指向Object(所有的引用类型都是Object的子类).而原型中的属性则和调用实例的属性并无差别,需要注意的时,存在同名属性时,实例的属性会覆盖原型属性,即,会先从实例本身开始查找属性,找不到的情况下才会去原型中寻找。
存疑如下
function test(){}; test.prototype; 输出:Object {} test.prototype.__proto__ 输出:Object {} test.__proto__; 输出:function(){}
test.prototype.__proto__ == Object.prototype 输出:true
首先,test的prototype是object,这没有问题,是引用类型。然后,test的原型中所包含的__proto__指针,指向了Object的prototype,这也没太大问题,因为test的prototype是Object的子类.然而,test中也包含了一个子类中会包含的__proto__指针,而输出是function。
目前强行理解如下:
function也算是一个构造函数,而且是通过function 函数名(){}来创建子类,所以其中会包含__proto__指针,并且指向function(){}。(其实很奇怪,因为按理来说不是应该指向function的prototype,那么就应该还是Object()类型,而且function作为一个关键字,并不能查看到类似于function.prototype这样的东西,很难理解)
慢着,刚才通过浏览器的console查看到了test.__proto__的属性
test.__proto__.constructor 输出: function Function() { [native code] },那么至少可以确定一点,即,我们声明的函数的的确确是这个Funtion的子类(注意是大写),的确,里面还有其他一些函数特有的属性,比如caller,arguments,apply.
书上的解释。
原来Function也是一个类型,而我们所用的函数实际上就是一个个的对象,是Function的实例。因此函数名实际上也是一个指向函数对象的指针。
茅塞顿开的一行来了!
Function.prototype.__proto__ == Object.prototype 输出: true
那么答案很简单了,Function也是一个类型,并且也是Object的子类。那么唯一的疑惑大概就是,为什么Function.prototype是function,而不是Object,不过也不算难点。因为prototype是可以赋值的,那么既然Function也是Object的子类,那么完全可以将Function的原型去赋一个function的值,并且也只需要将这个function的__proto__属性指向Object的prototype即可。只是不知道javascript为什么要这么做。