- JScript code
<html><head><script type=”text/javascript”><!–var00 = 0;document.write(var00 + ‘<br>’);var01 = 1;//A:全局变量是吧function foo(){ document.write(var01 + ‘<br>’); //B:
是调用A处的全局变量吧,为什么最后的输出结果是‘undefined’呢??? var var01 = 2; var03=3; var var04 = 4}foo();document.write(var01 + ‘<br>’)document.write(var03 + ‘<br>’)document.write(var04 + ‘<br>’)–></script></head><body></body>
</html>
就你的例子来进行说明:
1,JavaScript 的变量范围问题
JavaScript 有两种变量范围:全局和局部。如果在任何函数定义之外声明了一个变量,
则该变量为全局变量,且该变量的值在整个持续范围内都可以访问和修改。如果在函数定
义内声明了一个变量,则该变量为局部变量。每次执行该函数时都会创建和破坏该变量;
且它不能被该函数外的任何事物访问。这一点没有任何问题,大家的理解都不会出现问题。
2,一个局部变量的名称可以与某个全局变量的名称相同,但这是完全不同和独立的两个变量。
因此,更改一个变量的值不会影响另一个变量的值。在声明局部变量的函数内,只有该局部变量有意义
。你的问题就是出现在这个地方。在你的函数foo()里又进行了定义 var var01 = 1;
这才是你出现问题的原因所在。JavaScript 不是按顺序执行的吗?以上代码为什么会出错?
这是一个很令人迷惑的地方,也是从你的例子执行结果为undefined 而百思不得其解的原因。
请继续看下面的一条规则。
3,当 JavaScript 运行函数时,首先查找所有的变量声明,并以未定义的初始值创建变量。
如果变量被声明时有值,那么该变量仍以未定义的值初始化,并且只有在运行了声明行时才被声明值取代
,假如曾经被声明过。也就是说,你在foo()里又定义了一次 var var01 = 1;,
此时,var01 被看作是局部变量了,和外面的var01已经不是同一个变量了。
所以,document.write(var01) 的结果首先要肯定不是外面的 1。
好,就算是局部变量,我在foo()里已经赋值为 1 了,为什么结果还是 undefined ?
仔细看一下本段前面的说明,“首先查找所有的变量声明,并以未定义的初始值创建变量”,
即使你在foo()里进行了var01赋值,但 JavaScript 代码执行时,知道了你定义了变量
(因为此时没有报“变量未定义”错误),但没有执行到赋值语句时,是没有值的,
所以才出现 undefined 的结果。
4,JavaScript变量声明:变量在脚本中的第一次出现是在声明中。
变量在第一次用到时就设置于内存中,便于后来在脚本中引用。
使用变量之前先进行声明。可以使用 var 关键字来进行变量声明。
如果在 var 语句中没有初始化变量,变量自动取 JScript 值 undefined。尽管并不安全,
但声明语句中忽略 var 关键字是合法的 JScript 语法。
这时,JScript 解释器给予变量全局范围的可见度。
如果变量是在函数中显式声明的 — 也就是说,
如果它出现于赋值表达式的左边但没有用 var 声明 — 那么将把它创建为全局变量
JScript code<html><head><script language=”javascript” type=”text/javascript”><!–var00 = 0;document.write(var00 + ‘<br>’);var01 = 1;//A:全局变量是吧function foo(){ document.write(var01); //B:是调用A处的全局变量吧,
为什么最后的输出结果是‘undefined’呢??? var var01 = 1;}foo();–></script></head><body></body></html>/*简单点说。。javascript开始执行前,它会解释所有已声明的变里,,顺序如下:1. var00 –>已声明2. var01 –> 已声明 —>关键所在。3. 函数内部var var01=1; —>所有这里已声明。。可以把这个看成两步var var01 ;var01=1;
先会执行var var01;但发现 发现第2步( 指全局var01) 已经声明。所以会在其内部把全局变量隐藏掉了。但此里又没有附值给var01附值会在 document.write(var01); 执行后,执行。。*/
什么是域?就是scope,我们平常所说的变量作用域,不过通常直接叫做域。
在JavaScript当中,只有function是域的分界,如果那篇文章告诉你循环也能作为域的分界,
那就是错误的。
那么域只能有一层?错,JavaScript里面function能够套function,例如:
var v;
function myObject() {
var v;
this.myMethod = function() {
var v;
alert(v);
}
}
关于变量的引用,从最内层域开始向外搜索,直到找到同名定义为止,
如果到了全局域都找不到定义,变量就是未定义。例如alert(v)里面的v,
就是最内层的var v。如果这个var v去掉,就是中间层的var v。如果也去掉,
就是最外层的var v。
转载请注明:夜阑小雨 » JavaScript 的变量范围问题