预编译

@compiler
js执行过程
语法分析
预编译
解释执行
[]分析下列代码执行情况
let res = add(3, 2);//5
console.log(res);
function add(a, b) {
  return a + b;
}
[]分析下列代码执行情况
console.log(a);
var a = 123;//undefined
[]分析下列代码执行情况
console.log(a);
let a = 123;//Uncaught ReferenceError: Cannot access 'a' before initialization
[]分析下列代码执行情况
console.log(a);//f a()
function a() {
}
var a = 123;
特点
函数提升
变量 声明var提升
补充
1.暗示全局变量imply global:如果变量没有声明就直接赋值使用,默认就是全局变量,属于window属性
a = 12;
console.log(a);
console.log(window.a);
2.一切声明的全局变量都是window属性
var a = 12;//全局变量
function fn() {
  var b = 20;//局部变量
}
console.log(a);
console.log(b);
      
函数预编译 AO
.函数预编译发生在函数执行的前一刻
.函数只有执行才会进行预编译
.函数的执行过程就是不断的更新AO属性
过程
1.创建AO-Active Object,构建执行期上下文
2.查找所有的形参和变量声明,做为AO的属性,并赋值为undefined;如果有重名的,则覆盖
3.将实参和形参关联起来,覆盖形参的undefined
4.查找函数声明,其值为函数体
5.从头开始执行函数其它语句
[]分析下列代码执行情况
function fn(a) {
  console.log(a);
  var a = 123;
  console.log(a);
  function a() { }
  console.log(a);
  var b = function () { }
  console.log(b);
  function d() { }
}
fn(1);
执行结果
ƒ a() { }
123
123
ƒ () { }
      
全局预编译 GO
说明
.全局编译过程中,生成的是GO-Global Object,等同样window,过程同函数预编译
.数据更新过程中,先查找AO,如果没有,再向上查找GO
[]分析下列代码执行情况
a = 100;
function fn() {
  console.log(a);
  a = 200;
  console.log(a);
  var a = 300;
}
fn();
var a;
执行结果:函数fn内部有变量a的声明,所以不会跑去GO中查看
undefined
200
[]分析下列代码执行情况
.c没有显式变量声明,提升至GO
// GO{
//   a: undefined
//   fn: f
//   c: 234
// }
function fn() {
  console.log(b);//undefined
  if (a) {//a为undefined;条件不成立,所以b仍为undefined
    var b = 100;
  }
  console.log(b)//undefined;
  c = 234;
  console.log(c)//234;
}
var a;
// AO{
//   b: undefined
// }
fn();
a = 10;
console.log(c);//234