zoukankan      html  css  js  c++  java
  • 函数声明与函数表达式

    函数声明与函数表达式

    定义一个函数的方法主要有三种 函数声明、函数表达式、new Function构造函数,函数声明与函数表达式定义的函数较为常用,构造函数的方式可以将字符串定义为函数

    函数声明

    函数声明会将声明与赋值都提前,也就是整个函数体都会被提升到作用域顶部

    s(); // 1
    function s(){
        console.log(1);
    }
    

    也就是说,在某个作用域中定义的函数可以在这个作用域的任意位置调用,整个函数体都将被提前,当然也有不一样的情况:

    console.log(s); // undefined // 函数的声明提升但是并未赋值函数体
    console.log(ss); // Uncaught ReferenceError: ss is not defined // 打印未定义的ss是为了对比说明函数的声明提升
    s(); // Uncaught TypeError: s is not a function
    if(1){
        function s(){
            console.log(1);
        }
    }
    

    此处可以看到函数的声明被提升,但是函数体并未被提升,JS只有函数作用域与全局作用域以及ES6引入的letconst块级作用域,此处if不存在作用域的问题,为同一作用域,但是由于解释器在预处理期无法确定if里面的内容,所以只对函数声明的变量进行了提升,而并未将函数体赋值。

    函数表达式

    函数表达式只会提升变量的声明,本质上是变量提升并将一个匿名函数对象赋值给变量,

    console.log(s); // undefined
    var s = function s(){
        console.log(1);
    }
    console.log(s);  // f s(){console.log(1);}
    

    在JS引擎的执行的优先级是 变量声明 函数声明 变量赋值

    console.log(s); // ƒ s(){console.log(1);}
    var s = function(){
        console.log(0);
    }
    function s(){
        console.log(1);
    }
    s(); // 0
    

    new Function

    new Function的方式可以将字符串解析为函数

    var s = new Function("a","b","console.log(a,b);");
    s(1,2); // 1,2
    console.log(s.__proto__ === Function.prototype); //true
    function ss(){} // 声明的函数都是Function的一个实例
    console.log(ss.constructor === Function); // true
    console.log(ss.__proto__ === Function.prototype); // true
    

    new Functioneval也有所不同,其对解析内容的运行环境的判定有所不同

    // eval中的代码执行时的作用域为当前作用域,它可以访问到函数中的局部变量,并沿着作用域链向上查找。
    // new Function中的代码执行时的作用域为全局作用域,无法访问函数内的局部变量。
    var a = 'Global Scope';
    (function b(){
        var a = 'Local Scope';
        eval("console.log(a)"); //Local Scope
        (new Function("console.log(a)"))() //Global Scope
    })();
    
  • 相关阅读:
    解决使用gomod后goland导包报红问题
    Golang写文件的坑
    Golang去除字符串前后空格
    Golang通过结构体解析和封装XML
    Golang获取CPU、内存、硬盘使用率
    Golang数组和切片的区别
    Golang修改操作系统时间
    Golang中GBK和UTF8编码格式互转
    Golang中的各种时间操作
    Golang十六进制字符串和byte数组互转
  • 原文地址:https://www.cnblogs.com/WindrunnerMax/p/12558458.html
Copyright © 2011-2022 走看看