美文网首页首页投稿(暂停使用,暂停投稿)
浅谈JavaScript 函数作用域当中的“提升”现象

浅谈JavaScript 函数作用域当中的“提升”现象

作者: 车大棒 | 来源:发表于2016-11-14 11:27 被阅读152次

在JavaScript当中,定义变量通过var操作符+变量名。但是不加 var 操作符,直接赋值也是可以的。
例如 : message = "hello JavaScript ! " 即定义了一个全局变量message,并赋值 “Hello JavaScript!”
--《JavaScript高级程序第三版》

如同往日一般,一群人在所谓的技术交流群里面相互斗图着。突然老王莫名的正经起来,在群里发了一道JavaScript的题目,让大家猜一猜这道题的答案。

var foo = 1;
    function bar() {
        foo = 10;
        return;
        function foo() {}
    }
    bar();
    console.log(foo);  //求控制台输出多少?

看到这到题目之后,立刻不加思索回答了“10”。
首先第一步定义一个全局变量foo = 1,然后函数执行的时候又定义全局变量 foo = 10覆盖了之前的全局变量,return之后,这个函数就直接结束, function foo {}来不及定义。因此控制台输出10;
按照在《高三》上面看到知识点推断,毫无问题,简直完美呀!

给自己32个赞!

但是,在把答案发出去之后。本能就感觉这道题不可能这么简单,不正经的群突然讨论正经的代码,肯定会有大坑等着人来跳。一种不好感觉涌上心头,感觉自己又要被打脸了。

赶紧打开编辑器测试一下这段代码,手哆嗦的按下F12.只见控制台下,一个耀眼的1赫然闯入眼帘。啪啪啪!!这脸又被打的,好疼呀!!

为什么被打脸的总是我!!

果不其然群里老王马上的在群里否决我的答案,啪的一下打了这张老脸。
不行!这个脸打了得把场子找回来,这个老王接下来肯定会揭晓答案并公布解题思路。得在他公布之前,讲答案和原因给测试出来。

经过简单的测试之后,发现原来是后面的foo,函数提升到最顶端了。所以后面foo = 10中的foo实际上是一个局部变量了。因此后面console.log(foo)时是拿不到bar函数中的局部变量foo = 10,因此只能拿到全局变量foo = 1;所以控制台输出1。

上文代码的另外一种形式:
var foo = 1;
    function bar() {
        function foo(){}
        foo = 10;
        return;
    //  function foo() {}    相当于这行代码提升到最顶部了
    }
    bar();
    console.log(foo); 

被抢了风头的老王果断的不服气呀!说我瞎猜扯犊子一厢情愿的,自己随意猜想的。
好的,下面就是开始解释我为什么说函数function foo(){}提升到最顶端。不改动老王的代码,让我们只是加两个console.log测试一下相应的输出结果。

var foo = 1;
    console.log("全局变量:foo = " + window.foo)
    function bar() {
        console.log("此时bar函数中foo =" + foo)
        foo = 10;
        console.log("bar函数中的变量是" + foo);
        console.log("全局变量foo还是:"+window.foo);
        return;
        function foo() {}
    }
    bar();
    console.log(foo); 
浏览器输出结果
浏览器测试结果

通过这里可以证实我的猜想是正确的,function foo(){}直接被提升到bar()函数最顶端,然后后面foo = 10就不是再重新定义全局变量了,这里foo是一个局部变量的角色被定义出现的。因此才没有将全局变量给覆盖,而由于函数外面是不能直接拿到bar函数当中的局部变量foo,因此继续向上寻找到全局变量foo = 1.从而输出1.

我脸都这么红了,应该不用打脸了

这里估计联想能力丰富的小伙伴肯定会举手说,那么函数有提升的现象。那么变量也是否会有提升现象?不错!不错!!这位小伙伴联想的非常正确,学习就要多学会举一反三。

奖励一朵小红花
变量提升
var foo = 1;
    function bar() {
        foo = 10;
        return;
        var foo   //几乎是相同的代码,只是把 function foo  变成了   var  foo。变量也是能够提升了的!
    }
    bar();
    console.log(foo);  //还是输出1.
思考:

同样的既然变量能够提升,函数声明能够提升。那么谁升的更高呢?

function test(){
        console.log(dabang);
        function dabang(){};
        var dabang;
    }
    test();
    
function test1(){
        console.log(dabang);
        var dabang;
        function dabang(){};
        
    }
    test1();

控制台输出结果:

大棒声明的函数那必须升的高呀!!!
小结:

1、在JavaScript当中,函数作用域当中。变量和声明函数都能够提升。
2、同样提升的情况下,声明函数提升的更加高!

以上就是鄙人对于JavaScript函数作用域中“提升现象”一点简单理解,欢迎各位的大佬们指导学习。
ps:打脸也是可以的,毕竟错了就是错了。(那是打脸可否轻一点,留着日后再打呀!(~ ̄▽ ̄)~)

吾虽浪迹天涯,却从未迷失本心!吾虽恶搞不断,却不敢胡乱代码!

相关文章

  • 浅谈JavaScript 函数作用域当中的“提升”现象

    在JavaScript当中,定义变量通过var操作符+变量名。但是不加 var 操作符,直接赋值也是可以的。例如 ...

  • 2019-11-11-本周学习周报

    学习总览 JavaScript 函数作用域、块级作用域 变量提升、函数提升 CSS 新增属性transition ...

  • 块作用域和let、const

    在ES6之前,JavaScript没有块级作用域,只有全局作用域和函数作用域。 变量提升即将变量声明提升到它所在作...

  • js 基础

    JavaScript 函数 是对象 函数提升 提升作用域 在声明前调用。 自调用 (不能自调用声明的函数) 表达...

  • JavaScript函数作用域和声明提前

    函数作用域 JavaScript 中没有块级作用域,JavaScript 取而代之地使用了函数作用域。变量在声明它...

  • JavaScript 变量提升和函数提升

    一、变量提升 在ES6之前,JavaScript没有块级作用域,只有全局作用域和函数作用域。 1.所指的形式:必须...

  • JavaScript作用域学习笔记

    @(JS技巧)[JavaScript, 作用域] JavaScript作用域学习笔记 概念: 作用域就是变量与函数...

  • JavaScript - 变量作用域

    JavaScript教程之变量作用域 变量提升:JavaScript的函数定义有个特点,它会先扫描整个函数体的语句...

  • js 变量作用域问题 以及 let

    JavaScript中有以下两种作用域 全局作用域函数作用域全局作用域是函数之外(最外层代码)的作用域。在函数之外...

  • JavaScript 作用域和作用域链

    JavaScript 作用域 作用域就是变量与函数的可访问范围。在JavaScript中,变量的作用域有全局作用域...

网友评论

    本文标题:浅谈JavaScript 函数作用域当中的“提升”现象

    本文链接:https://www.haomeiwen.com/subject/sxkxpttx.html