重新认识Javascript

1.在函数内有没有var真的不一样

下面这样一段代码,在函数abc()中,创建了两个变量a, c,并在函数体之外进行alert,想看看有什么事发生:

1
2
3
4
5
6
7
8
<script>     
        function abc(){
            var a = "1";
            c = "3";
        }
        alert(a);
        alert(c);
</script>

结果,alert(a)的结果自然不出所料, 报错:未定义这个变量,因为这是一个局部变量, 超出了界限, 自然无法使用.

但alert(c)却能成功显示3, 这有点出乎意料, 一直以为var写不写都可以, 还以为写在function中的变量都是局部变量呢!  

如dolphinX所说的 "变量没有在函数内声明或者声明的时候没有带var就是全局变量,拥有全局作用域,window对象的所有属性拥有全局作用域;在代码任何地方都可以访问,函数内部声明并且以var修饰的变量就是局部变量,只能在函数体内使用,函数的参数虽然没有使用var但仍然是局部变量。"

 

2.Javascript只有函数级作用域, 没有块级作用域

再看一段:

1
2
3
4
5
6
7
8
9
10
if (true) {
    var n = 1;
}
alert(n); //1
 
 
function abc() {
    var a = "1";
}
alert(a); //报错a未定义

第二个alert报错a未定义 , 这个已经有心理准备了, 因为函数里加了var就是局部变量, 出了函数就不起作用了.

而第一个alert成功显示1, 却是为啥? 看了一些园友的好帖, 终于明白, 这是因为javascript没有块级作用域造成的.

下面这张图是c#代码, 在Form2()中if (4>2)语句块中定义的abc变量, 出了if语句块就无效了, 这就是块级作用域, 更不用提在testBox3_lostfocus()了, 更是无法使用abc变量, 这是函数级别作用域, 这些本来在c#, java中司空见惯的常识, 在javascript中却是行不通了.

重新认识Javascript

因为JavaScript没有块级作用域,这就意味着除了在函数中加var定义的变量, 其他的变量都是全局的了, 即: 函数外的加var或不加var, 函数内不加var, 和在if (4>2){}内定义的变量, 不管加不加var, 都是全局变量了. 也就是if (4>2)后{}, 就当没有这个层次罢了.

这个例子也证明了, javascript有函数级别作用域, 却没有块级作用域.

 

3.函数可以定义在后,执行在前,是JavaScript域解析的缘故.

接着再看一段代码: 

1
2
3
4
5
6
7
8
var a = "0";
abc();
function abc() {
    alert(a);
    var a = "1";          
    c = "3";           
}
alert(a);

我定义函数abc()在后,执行abc()却在前,这样没有问题,可以执行,为什么?

原来这叫预解析,借用dolphinX所说, "这是因为JavaScript是解释型语言,但它并不是直接逐步执行的,JavaScript解析过程分为先后两个阶段,一个是预处理阶段,另外一个就是执行阶段。在预处理阶段JavaScript解释器将完成把JavaScript脚本代码转换到字节码,然后第二阶段JavaScript解释器借助执行环境把字节码生成机械码,并顺序执行。也就说JavaScript值执行第一句语句之前就已经将函数/变量声明预处理了,这也是为什么我们可以在方法声明语句之前就调用方法的原因。"

函数abc()内的var a=”1” 相当于两个语句,var a; a=”1”。因为预处理函数abc()时已经将var a给解析执行了,所以到了正式执行alert(a)时,就报undefined的错误了,闹了半天是这么回事.

 
4.对象创建方法之一: Json方式

var person={};

var person={firstname:"John",lastname:"Doe",age:50,eyecolor:"blue"};

这两种创建对象的方式和

var person = new Object();

这种是等价的, {}对应object, 上面两种Json方式的创建对象被称作对象字面量.

 

5.立即执行函数, 匿名函数

打开jQuery或其他js类库都可以发现如下的代码:

1
2
3
4
5
(function(){
 
//jQuery类库或其他类库
 
})();

这里的两对括号, 第一对表示里面代码是一个匿名函数, 所谓匿名函数就是没有起名字的函数, 但它也是函数,如下: 

1
alert((function (x, y) { return x + y; }));

当这个匿名函数被第二对括号括起来,这个匿名函数就能立即运行了!  

类似如下: 

1
alert((function (x, y) { return x + y; })(2, 3));// "5"

 

6.闭包

重新认识Javascript,布布扣,bubuko.com

重新认识Javascript

上一篇:Java设计模式之观察者模式


下一篇:栈(Stack)的C++实现