js函数作用域

在console中,测试,不知道一下2个函数有什么区别,为什么name打印出来的结果不同?
clipboard.png

我理解不了

阅读 3.8k
7 个回答

1.首先要了解变量声明和函数声明提前
就是在执行函数时,会先查找函数内的var关键字 和 函数声明,并预编译。

function f(){
    console.log(1);
    var name = 'name';//此处var name 会被提前
    name2 = 'name2';
    function fun(){};//此处函数声明会被提前
    var fun2 = function(){};//此处var fun2 会被提前
}

执行顺序是

function f(){
    function fun(){};
    var name;
    var fun2;
    console.log(1);
    name = 'name';
    name = 'name2';
    fun2 = function(){};
}

就是声明被提前了,而赋值不会。
这是你的第二段程序输出结果不同的原因。

2.然后要了解作用域链的概念,即变量的查找过程,会先查找当前作用域,没有则会向上一级作用域查找;
如:

var a = 1;
(function test(){
    console.log(a)
    var a = 1
})();

实际执行顺序是

var a = 1;
(function test(){
    var a ;
    console.log(a);
    a = 2;
})();

在执行console.log(a)时,函数内已经声明了变量a(包括函数形参也属于声明了变量),但是未赋值,所以值为undefined,所以输出undefined;
而如果函数内没有变量a,则会找到外部的a,输出1;


可以系统的看下作用域链,上下文执行环境和预编译。

变量声明提前, hositing……

相当于:

var name = 'webLearner';
function f(){
    var name;
    console.log('1:'+name);
    name = "LuckyJing";
    console.log('2:'+name);
}
f();

这是个声明提前的坑,你f函数内部var了一个name,那么也就是说第一句console.log中的那个name变量其实是引用的f函数内这个新声明的变量,但是坑爹的是,它又有:声明提前,赋值保留在原地。这一特性,也就是说此时name的值为undefined,所以第一个console输出的就是undefined

第一段代码顺序执行,不多说了,你应该懂。
第二段代码涉及到了局部变量和声明提前两个概念。首先全局声明了一个name变量,值是weblearner。然后执行f的时候,在函数内部的实行顺序是这样的:
function f(){

var name;
console.log('1:'+name);
name='LuckyJing';
console.log('2:'+name);

}
声明提前就是执行一个函数的时候,无论变量在哪里声明,都会在执行function的时候先声明变量,但不赋值。由于是局部变量,会覆盖全局的name变量,就变成了undefined。此时执行到了第一个输出,就会输出undefined。接下来给局部的name赋值LuckyJing,执行输出。就得到你截图的结果了。

第一段代码不必考虑声明提前的问题。

这其实是 JavaScript 解析器搞的鬼,解析器将当前作用域内声明的所有变量和函数都会放到作用域的开始处,但是,只有变量的声明被提前到作用域的开始处了,而赋值操作被保留在原处。可以看看这个就明白了http://www.bootcss.com/articl...

首先声明变量用var,只要用了var 就会把这个变量提到最前面(这个作用于的最前面)
像你的第二个函数

function foo(){
console.log(name)
var name='123'
console.log(name)
}
foo()

js作用域是这样解析的

function foo(){
var name;
console.log(name)
name='123'
console.log(name)
}
foo()

所以结果会不一样,至于你在函数外面声明的变量和函数内容声明的变量不再一个作用域内,所以会有不一样的结果。

新手上路,请多包涵

var的声明提前

撰写回答
你尚未登录,登录后可以
  • 和开发者交流问题的细节
  • 关注并接收问题和回答的更新提醒
  • 参与内容的编辑和改进,让解决方法与时俱进
推荐问题
宣传栏