预编译四部:
1.创建GO/AO对象
2.找形参和变量声明,将变量和形参名作为AO属性名,值为undefined
3.将实参值和形参统一
4.在函数体里面找函数声明,值赋予函数体
(为了深刻理解预编译搬来自牛客的错题解析)
var foo = {n:1};
(function(foo){ //形参foo同实参foo一样指向同一片内存空间,这个空间里的n的值为1
var foo; //优先级低于形参,无效。
console.log(foo.n); //输出1
foo.n = 3; //形参与实参foo指向的内存空间里的n的值被改为3
foo = {n:2}; //形参foo指向了新的内存空间,里面n的值为2.
console.log(foo.n); //输出新的内存空间的n的值
})(foo);
console.log(foo.n); //实参foo的指向还是原来的内存空间,里面的n的值为3.
首先GO:foo={n:1}
function:
匿名函数执行时过程:上述很清晰
(模糊概念重新认识)
首先要认识执行期上下文:在函数执行前一刻会进行预编译,
运行期上下文(函数指的预编译产生的AO):
当一个函数执行时,会创建一个称为执行期上下文的内部对象。
一个执行期上下文定义了一个函数执行时的环境,函数每次执行时对应的执行上下文都是独一无二的,
多次调用一个函数会导致创建多个执行上下文,当函数执行完毕,他所产生的执行上下文被销毁。
[[scope]]:每个javascript函数都是一个对象,对象中有些属性我们可以访问,有些不可以,
这些属性仅供javascript引擎存取,[[scope]]就是其中一个。
[[scope]]:指的就是我们所说的作用域,其中存储了执行期上下文的集合。
作用域链:[[scope]]中所存储的执行期上下文对象的集合,这个集合呈链式连接,
我们把这种链式连接叫做作用域链。
总结·作用域链就是存储着执行期上下文的集合的链式连接。
原型:是function对象的一个属性,定义了构造函数制造出来的对象的公共祖先,
通过该构造函数产生的对象,可以继承该原型的属性和方法。
Person.prototype = {} --原型 --是构造函数构造出的对象的祖先
用new 来构造对象:
1、创建一个新对象
2、将构造函数的作用于赋给新对象(因此this指向新对象)
3、执行构造函数中的代码(为新对象添加属性)
4、返回新对象
function Person(){
1. var this = {// person = new Person()此时的this就是person
__proto__:Person.prototype//将自己和原型连接
};
}
把原型连成连,访问顺序按照连接顺序
原型链的连接点就是__proto__;
找属性值:如果自身没有,通过__proto__找他的原型