JavaScript的高级知识---词法分析

词法分析

词法分析方法:

js运行前有一个类似编译的过程即词法分析,词法分析主要有三个步骤:

  • 分析参数
  • 再分析变量的声明
  • 分析函数说明
  • 函数在运行的瞬间,生成一个活动对象(Active Object),简称AO
  • 分析参数

具体步骤如下:

  1. 函数接收形式参数,添加到AO的属性,并且这个时候值为undefine,例如AO.age=undefine
  2. 接收实参,添加到AO的属性,覆盖之前的undefine
  • 分析变量声明,如var age;或var age=23;
  1. 如果上一步分析参数中AO还没有age属性,则添加AO属性为undefine,即AO.age=undefine
  2. 如果AO上面已经有age属性了,则不作任何修改
  • 分析函数的声明,如果有function age(){}

把函数赋给AO.age ,覆盖上一步分析的值

代码例子1

这样我们先通过一段代码来理解词法分析:

<script>

function t1(age) {

console.log(age);

var age = 27;

console.log(age);

function age() {}

console.log(age);

}

t1(3);

</script>

词法分析阶段:

  • 首先形成Active Object即AO对象
  • 第一步:分析形式参数

AO.age = undefine

传入实参即对AO.age=undefine进行覆盖:

AO.age = 3

  • 第二步:分析局部变量

存在var age = 27;

这个时候遵循如果AO.age存在值则不作任何修改,按照第一步分析的最后结果AO.age = 3,所以这里不作任何修改即:

AO.age = 3

  • 第三步:分析函数的声明,

因为函数中存在function age(){}函数

所以按照规则应该将函数赋值给AO.age覆盖第二步分析的AO.age = 3即:

AO.age = function age(){}

执行阶段

执行t1函数,到console.log(age)时,词法分析的最后AO.age= function age(){},所以会打印:

function age(){}

var age=27;给age赋值27

到第二个console.log(age)这个时候age已经重新被赋值27,所以这个时候会打印:

27

function age() 并没有调用所以并不会执行

到第三个console.log(age)这个时候age的值并没有被再次修改,所以这个时候会打印:

27

运行js查看结果如下与我们分析的完全相符:

代码例子2

<script>

function t1(age) {

var age;

console.log(age);

var age = 23;

console.log(age);

function age() {}

console.log(age);

}

t1(22)

</script>

和上面的词法分析过程一样

词法分析阶段:

  • 首先形成Active Object即AO对象
  • 第一步:分析形式参数

AO.age = undefine

传入实参即对AO.age=undefine进行覆盖:

AO.age = 22

 

  • 第二步:分析局部变量

第一步中最后得到AO.age = 22

所以这里var age;以及var age =23 ,因为AO.age属性已经存在值,所以这个时候遵循如果存在则不作任何修改,即:

AO.age = 22

  • 第三步:分析函数的声明,

因为函数中存在function age(){}函数

所以按照规则应该将函数赋值给AO.age覆盖第二步分析的AO.age = 22即:

AO.age = function age(){}

执行阶段

执行t1函数,到console.log(age)时,词法分析的最后AO.age= function age(){},所以会打印:

function age(){}

var age=23;给age赋值23

到第二个console.log(age)这个时候age已经重新被赋值23,所以这个时候会打印:

23

function age() 并没有调用所以并不会执行

到第三个console.log(age)这个时候age的值并没有被再次修改,所以这个时候会打印:

23

运行js查看结果如下与我们分析的完全相符:

代码例子3

<script>

function t1(age) {

var age;

console.log(age);

age = 23;

console.log(age);

function age() {

console.log(age);

}

age();

console.log(age)

}

t1(22)

</script>

词法分析阶段:

  • 首先形成Active Object即AO对象
  • 第一步:分析形式参数

AO.age = undefine

传入实参即对AO.age=undefine进行覆盖:

AO.age = 22

 

  • 第二步:分析局部变量

第一步中最后得到AO.age = 22,所以这里遵循,如果AO.age存在值则不作任何修改即:

AO.age = 22

  • 第三步:分析函数的声明

因为函数中存在function age(){console.log(age)}函数

所以按照规则应该将函数赋值给AO.age覆盖第二步分析的AO.age = 22即:

AO.age = function age(){console.log(age)}

 

执行阶段

执行t1函数,到console.log(age)时,词法分析的最后AO.age= function age(){console.log(age)},所以会打印:

function age(){console.log(age)}

 

age = 23,这个时候会覆盖原来的function age(){console.log(age)},所以第二个console.log(age)会打印:

23

function age() 是一个函数表达式,所以不会做任何操作

age() 这个时候的age还是23,并不是函数表达式,所以这里会报错

运行js查看结果如下与我们分析的完全相符:

这里的提示错误确实也是说age不是一个函数

代码例子4

<script>

function t1(age) {

var age;

console.log(age);

function  age() {

console.log(age);

}

age();

console.log(age);

}

t1(23)

</script>

词法分析阶段:

  • 首先形成Active Object即AO对象
  • 第一步:分析形式参数

AO.age = undefine

传入实参即对AO.age=undefine进行覆盖:

AO.age = 23

  • 第二步:分析局部变量

第一步中最后得到AO.age = 23,所以这里遵循,如果AO.age存在值则不作任何修改即:

AO.age = 23

  • 第三步:分析函数的声明

因为函数中存在function age(){console.log(age)}函数

所以按照规则应该将函数赋值给AO.age覆盖第二步分析的AO.age = 23即:

AO.age = function age(){console.log(age)}

执行阶段

执行t1函数,到console.log(age)时,词法分析的最后AO.age= function age(){console.log(age)},所以会打印:

function age(){console.log(age)}

 

function age() 是一个函数表达式,所以不会做任何操作

 

age()这个时候age是一个函数表达式,这里会执行function age(){console.log(age)},这个时候函数里console.log(age),age没有被修改所以还是function age(){console.log(age)},即打印:

function age(){console.log(age)}

 

最后一个console.log(age)这里的age没有被修改还是function age(){console.log(age)},所以会打印:

function age(){console.log(age)}

运行js查看结果如下与我们分析的完全相符:

代码例子5:

<script>

function t1(age) {

console.log(age);

var age = function () {

console.log(age)

}

age();

console.log(age);

}

t1(23);

</script>

词法分析阶段:

  • 首先形成Active Object即AO对象
  • 第一步:分析形式参数

AO.age = undefine

传入实参即对AO.age=undefine进行覆盖:

AO.age = 23

 

  • 第二步:分析局部变量

第一步中最后得到AO.age = 23,所以这里遵循,如果AO.age存在值则不作任何修改即:

AO.age = 23

  • 第三步:分析函数的声明

这里并没有函数声明表达式

所以最后分析的结果是:

AO.age = 23

执行阶段

执行t1函数,到console.log(age)时,词法分析的最后AO.age=23

所以第一个console.log(age)会打印

23

var age = function () {console.log(age)},这里将var = 23进行覆盖这个时候age是一个函数表达式

age() 正好调用function () {console.log(age)},这个时候这个函数里的console.log(age),age并没有修改还是一个函数表达式,所以会打印

function () {console.log(age)}

最后一个console.log(age)还是打印:

function () {console.log(age)}

运行js查看结果如下与我们分析的完全相符:

代码例子6:

<script>

function t1(age) {

console.log(age);

var age = function age() {

console.log(age);

}

age();

console.log(age);

}

t1(23);

</script>

代码例子6和代码例子5的分析基本一样,结果也是一样:

JavaScript的高级知识---词法分析的更多相关文章

  1. python成长之路【第十六篇】:JavaScript的高级知识---词法分析

    一.词法分析方法 js运行前有一个类似编译的过程即词法分析,词法分析主要有三个步骤: 分析参数 再分析变量的声明 分析函数说明 二.具体步骤如下: 函数在运行的瞬间,生成一个活动对象(Active O ...

  2. js的高级知识---词法分析

    词法分析 词法分析方法: js运行前有一个类似编译的过程即词法分析,词法分析主要有三个步骤: 分析参数 再分析变量的声明 分析函数说明 具体步骤如下: 函数在运行的瞬间,生成一个活动对象(Active ...

  3. 第十九篇 js高级知识---词法分析和AO 链

    上面一篇文章说了js的作用域链,这一节算是对上面的延申,有一个典型的例子,首先看原来的一段代码: var name = "test"; function t() { var b = ...

  4. js高级知识---词法分析和AO 链

    转载自https://www.cnblogs.com/OceanHeaven/p/4957704.html 上面一篇文章说了js的作用域链,这一节算是对上面的延申,有一个典型的例子,首先看原来的一段代 ...

  5. 快速掌握JavaScript面试基础知识(二)

    译者按: 总结了大量JavaScript基本知识点,很有用! 原文: The Definitive JavaScript Handbook for your next developer interv ...

  6. 潭州学院-JavaVIP的Javascript的高级进阶-KeKe老师

    潭州学院-JavaVIP的Javascript的高级进阶-KeKe老师 讲的不错,可以学习 下面是教程的目录截图: 下载地址:http://www.fu83.cn/thread-283-1-1.htm ...

  7. 自理一遍android 高级知识

    之后按目录得复习巩固 目录: 客卓高级知识整理 1 移动架构 1.1 素养与基础 1.1.1 主流设计模式 创建型 行为型 结构型 1.1.2 UML 1.1.3 设计原则 1.1.4 AOP架构 1 ...

  8. DataBase MongoDB高级知识-易使用

    MongoDB高级知识-易使用 mongodb是一个面向文档的数据库,而不是关系型数据库.不采用关系模型主要是为了获取更好的扩展性.当然还有其他的一些好处. 与关系型数据库相比,面向文档的数据库不再有 ...

  9. DataBase MongoDB高级知识-易扩展

    MongoDB高级知识-易扩展 应用程序数据集的大小正在以不可思议的速度增长.随着可用宽带的增长和存储器价格的下跌,即使是一个小规模的应用程序,需要存储的数据也可能大的惊人,甚至超出了很多数据库的处理 ...

随机推荐

  1. 201671010140. 2016-2017-2 《Java程序设计》java学习第五周

    java学习第五周心得体会        本周,是Java学习第五周,随着时间推移,随着课本内容的推进,我们接触到的程序也开始变得越来越复杂,不再是二三章那些用来练手的小程序了,这一点,在我们的例题运 ...

  2. Android中dp、dpi与px的关系

    转自知乎用户的回答: 1. dpi是dot per inch,每英寸多少点,ppi是 Pixel per inch,每英寸像素数,针对显示器的设计时,dpi=ppi.ppi计算方法是长宽各自平方之和开 ...

  3. 217. Contains Duplicate数组重复元素 123

    [抄题]: Given an array of integers, find if the array contains any duplicates. Your function should re ...

  4. 图解KMP算法

  5. Python学友

    独学而无友,则孤陋而寡闻,python学习过程中希望多和学友交流,一起进步. 开源中国 j_hao104 微信公众号: Pythoner每日一报 https://my.oschina.net/jhao ...

  6. python3--生成器并行运算

    # Auther: Aaron Fan """def consumer(name): print("%s 准备吃包子啦!" % name) while ...

  7. 验证码测试-demo

    <!DOCTYPE html><html><head><meta charset="UTF-8"><title>Inse ...

  8. 《深度学习原理与TensorFlow实践》喻俨,莫瑜

    1. 深度学习简介 2. TensorFlow系统介绍 3. Hello TensorFlow 4. CNN看懂世界 5. RNN能说会道 6. CNN LSTM看图说话 7. 损失函数与优化算法 T ...

  9. 如何杀死一个已经detached的screen会话?

    如果向杀死一个已经detached的screen会话,可以使用以下命令: screen -X -S seesion-id quit 举例如下: [root@localhost ~]# screen - ...

  10. 求整数数组(长度为n),出现大于2/n次数的数字

    条件:时间复杂度是O(n),空间复杂度是O(1) 方法1:标记法 , , , , , , , , , , , , , }; int len = arr.Length; int[] c = new in ...