- 浏览: 226028 次
- 性别:
- 来自: 广州
-
文章分类
最新评论
-
zzhyq:
有没有后台是ASHX 的呀
Ext.tree.TreePanel -
693593336:
谢谢作者分享,正好用上
Ext.tree.TreePanel -
greatwqs:
提供一个下载的demo不是更好
基于servlet的 Freemarker Demo
copy from :
http://www.blogjava.net/JAVA-HE/archive/2010/10/09/334021.html
这个话题看似简单,其实笔者是几次三番的下笔,又几次三番的放弃。因为这个内容,对于很多JavaScript的开发人员来讲都是一知半解的,当然笔者也在其中,今天之所以出来献丑了,首先是有了更深的认识,其次微博上有人说“献丑是进步”,如果献丑那必定是有同道之人能指出纰漏,那对于笔者本人来讲何尝不是进步呢?深表赞同!
今天会以几个小小的实例来解读这个课题。希望能与大家共勉。
首先得先了解JavaScript执行起来的流程,笔者先简单画了一个javascript的执行流程图:

重点解释的有三步:词法分析、预解析、执行。
script代码段:用script标签分隔的js代码或引入的js文件。
(1). 预解析
我们先从几个常见的javascript 小题目入手,请大家先看看下面的范例输出什么?
<script type="text/javascript">
alert(i); // ?
var i = 1;
</script>
对于javascript的从业者可以试着运行下。看看你的答案和实际输出一致吗?别小看这样两行脚本,这样的题目被当作JavaScript的笔试或者面试题目是常有的事情。
实际输出结果为:“undefined”,
这种现象被称成“预解析”:JavaScript脚本引擎优先解析var变量和function定义。在预解析完成后,才会执行代码。
由于变量i 是被 var声明的,而被优先解析。所以可以理解为在 alert(i) 执行时候,程序前面已经有 var i;
所以上面代码等效解释为:
<script type="text/javascript">
var i;
alert(i); // 对于被声明,但未赋值过的i,输出‘undefined’的结果,是不应该有任何歧义了吧。
i = 1;
</script>
注意:预解析不会报错,因为他只解析正确的声明。
(2). 解释(主要指词法分析,生成语法树的过程)
请注意,这里‘解释’的定义是笔者自己方便理解自己定义的,而这个‘解释’并不在预解析之后。
我们知道JavaScript是脚本语言,脚本语言是相对于高级编译型语言而言他是解释性的。解释性语言没有编译成二进制代码,但是要进入到运行阶段,都应该是会经过词法分析、语法分析生成语法树、语义检查过程,笔者把这个环节叫做“解释”,如果读者有更科学的名字记得告诉我。
解释性语言在生成语法树后,就可以执行了。(这个跟脚本引擎编译器有关)
在这个过程中,有语法检查(比如括号是否匹配),发现无法生成语法树,则报错,结束整个代码块的解析。
(3) 执行 与 作用域
引入我们的第二个示例代码:
<script type="text/javascript">
alert(i); // error: i is not defined.
i = 1;
</script>
听说JavaScript 变量可以直接用,那为什么还报运行时脚本错误?—— i 未定义.
执行过程,需要理解JavaScript的作用域机制,JavaScript变量的作用域是在定义时决定而不是执行时决定,也就是说词法作用域取决于源码,编译器通过静态分析就能确定,因此词法作用域也叫做静态作用域(static scope)。但需要注意,with和eval的语义无法仅通过静态技术实现,实际上,只能说JS的作用域机制非常接近lexical scope.
JS引擎在执行每个函数实例时,都会创建一个执行环境(execution context)。execution context中包含一个调用对象(call object), 调用对象是一个scriptObject结构,用来保存内部变量表varDecls、内嵌函数表funDecls、父级引用列表upvalue等语法分析结构(注意:varDecls和funDecls等信息是在预解析阶段就已经得到,并保存在语法树中。函数实例执行时,会将这些信息从语法树复制到scriptObject上)。scriptObject是与函数相关的一套静态系统,与函数实例的生命周期保持一致。
lexical scope是JS的作用域机制,还需要理解它的实现方法,这就是作用域链(scope chain)。scope chain是一个name lookup机制,首先在当前执行环境的scriptObject中寻找,没找到,则顺着upvalue到父级scriptObject中寻找,一直lookup到全局调用对象(global object)。
当一个函数实例执行时,会创建或关联到一个闭包(closure)。 scriptObject用来静态保存与函数相关的变量表,closure则在执行期动态保存这些变量表及其运行值。closure的生命周期有可能比函数实例长。函数实例在活动引用为空后会自动销毁,closure则要等要数据引用为空后,由JS引擎回收(有些情况下不会自动回收,就导致了内存泄漏)。
别被上面的一堆名词吓住,一旦理解了执行环境、调用对象、闭包、词法作用域、作用域链这些概念,JS语言的很多现象都能迎刃而解。
小结
“预解析”,其实是在的‘解释’阶段完成,并存储在语法树中。当执行到函数实例时,会将varDelcs和funcDecls从语法树中复制到执行环境的scriptObject上。
对于示例解析:
未定义变量意味着在scriptObject的变量表中找不到,JS引擎会沿着scriptObject的upvalue往上寻找,如果都没找到,对于写操作i = 1; 最后就会等价为 window.i = 1; 给window对象新增了一个属性。对于读操作,如果一直追溯到全局执行环境的scriptObject上都找不到,就会产生运行期错误。
最后,留个问题给大家:
<script type="text/javascript">
var arg = 1;
function foo(arg) {
alert(arg);
var arg = 2;
}
foo(3);
</script>
请问alert的输出是什么?
发表评论
-
JavaScript Core chapter 10
2011-07-18 11:20 896一些基础概念: #1 JavaScript 对象其实就是属 ... -
走马观花记二--css
2010-04-28 00:52 842css是Cascading Style Sheet(层叠样式 ... -
一个简单的Ajax登录例子
2010-06-27 10:12 9891.view(loginAjax.jsp) Code ... -
ajax的一些实例
2010-06-27 14:18 744两种引用方法: Code: //1 ... -
XHTML走马观花
2010-06-27 14:53 801其设计目的是为了实现从HTML到XML过渡,它结合了XML中部 ... -
CSS的一些实用例子
2010-06-27 15:35 738// 结合脚本语言动态的控制元素在页面中出现的位置。 ... -
DOM简介
2010-06-28 16:04 799全称是文档对象模型(Document Object Mode ... -
XML和XSTL走马观花(ajax)
2010-06-28 17:05 1250eXtensible Markup Language 的简称。 ... -
js中button事件的简单示例
2010-10-31 10:25 1177Code: <!DOCTYPEhtmlP ... -
一个简单的验证带验证提示例子
2010-11-05 23:47 848该例子的源码来源于《锋利的JQuery》这本书。Jquery ... -
网站开发必知基础(html)
2010-11-25 08:59 8311.div 定义和用法 <div> 可定义文档 ... -
Div+CSS布局入门教程
2010-12-07 23:40 752作为一个Web开发人员, ... -
jquery实例—json/xml数据格式交互
2011-04-07 10:08 1020学习资料:jquery实例 来自:http://www.doc ... -
jquery版本对json数据格式接收的区别
2011-04-08 14:46 1413毕设中,做注册页面,选用jquery纯属玩玩而已的,也不知道j ... -
56个民族 下来框(常用的排序)
2011-04-08 17:12 1594<select name="select&qu ... -
js获取当前url的中文参数
2011-04-14 02:50 2883问题源自于大傻同学的需求:A.html的参数传给B.html ... -
毕设简单的登录界面
2011-04-14 11:08 1019Code: <htmlxmlns=&qu ...
相关推荐
扩展机制演示这是使用延迟加载模块的Angular扩展机制的示例。构建扩展cd extensionnpm inpm run build运行应用程序cd platformnpm inpm start打开浏览器并导航到
It provides a powerful mechanism for processing collections, allowing for parallel operations, filtering, mapping, and reducing data in a functional and declarative manner. This has greatly improved ...
5. **Nashorn JavaScript Engine**: JDK 1.8 includes the Nashorn JavaScript engine, allowing developers to run JavaScript code directly within the JVM. This integration facilitates interoperability ...
Networking Override Mechanism Security Serialization Extension Mechanism XML JAXP lang and util Base Libraries lang and util Collections Concurrency Utilities JAR Logging Management Preferences ...
Defines the jlink tool for creating run-time images, the jmod tool for creating and manipulating JMOD files, and the jimage tool for inspecting the JDK implementation-specific container file for ...
- **Feature Receivers:** Event handlers that run when features are activated or deactivated. - **Handling FeatureUpgrading Events:** Techniques for managing feature upgrades during SharePoint upgrades...
If you where slick, you would place the configuration information into a file and load the file at run time. Function pointer arrays were the good old days of structured programming in C. Life is ...
Output buffering is a mechanism for controlling how much output data ; (excluding headers and cookies) PHP should keep internally before pushing that ; data to the client. If your application's ...