关于javascript:作用域

31次阅读

共计 2305 个字符,预计需要花费 6 分钟才能阅读完成。

1. 作用域概述

通常来说,一段程序代码中所用到的名字并不总是无效和可用的,而限定这个 名字(变量)的可用性的代码范畴就是这个名字的作用域,作用域的应用进步了程序逻辑的局部性,加强了程序的可靠性,缩小了名字抵触

1.1.js 作用域(es6 之前)分为:全局作用域 部分作用域

1.2. 全局作用域:整个 script 标签 或者是一个独自的 js 文件

       var num = 10 ;(这一个标签是写在全局作用域外面 这个变量名是可用的 称之为全局作用域)

1.3. 部分作用域(函数作用域):在函数外部就是部分作用域,这个代码的名字只在函数外部起成果和作用

 var num = 10  // 部分作用域
 function fn(){
  // 部分作用域
   var num = 20 ; // 部分下的 num 和全局下的 num 是不抵触的因为输入的不一样
   console.log(num) //20
 }
 fn()  // 切记调用
 console.log(num) // 10
 

2. 变量作用域

在 js 中,依据作用域的不同,变量能够分为俩种:全局变量,局部变量

2.1. 全局变量:在全局作用域下的变量 在全局下都能够应用(在函数内部定义的变量)(3. 非凡状况留神一下:如果在函数外部,没有申明间接赋值的变量也属于全局变量)

  var num=10;
  console.log(num);// 能够打印  10 
  function fn(){ // 函数
    console.log(num)// 也是能够打印的 10 
           }
           fn()
            console.log(aru) //4.aru is not defined   不能应用

2.2. 局部变量:在部分作用域下的变量 或者能够了解为在函数外部的变量就是局部变量(在函数外部定义的变量)(留神:函数的形参也能够看做是局部变量 4.aru 是一个形参)

function fun(aru){
  var num = 10; //1.num 就是局部变量 特点就是只能在函数外部应用
  num = 20; //3 . 如果在函数外部,没有申明(不实用 var)间接赋值的变量也属于全局变量
}
fun();
console.log(num);  //2.num is not defined 报错  所以说内部是不能应用的
console.log(num); //3. 20 如果在函数外部,没有申明间接赋值的变量也属于全局变量

2.3. 区别:从执行效率来看全局变量和局部变量
(1)全局变量在任何一个中央都能够应用,只有浏览器敞开的时候才会销毁,比拟占内存资源
(2)局部变量 当咱们程序执行结束就会销毁,比拟节约内存资源

3. 作用域链

3.1. 只有是代码,就至多有一个作用域

var num = 10; // 全局作用域

3.2. 在函数外部的叫做部分作用域

var num = 10;
function fun(){  // 内部函数
  var num = 20; 
  function fn(){//3.3. 在 fun 函数外面有生成了一个 fn 函数   作用域外面诞生了一个新的作用域   外部函数
  console.log(num);//3.4. 执行是 20 还是 10 呢 20  用链式查找决定  它会往上一级找有没有 num 一层一层的找就是链式查找
   }
   fn()}
fun()

3.3. 如果函数中还有函数,那么在这个作用域中就有能够诞生一个作用域

3.4. 依据在外部函数能够拜访内部函数变量的这种机制,用链式查找决定哪些数据能被外部函数拜访,就称为作用域链 (简略了解就是就近准则,谁离的近就执行谁)

案例 1:

function f1(){   //1  能够称为 0 级链
  var num = 123;    //2  能够称为 1 级链
  function f2(){    //2  能够称为 1 级链
     console.log(num);    //3 能够称为 2 级链       123
  }  
  f2()}
var num = 456;  //1 能够称为 0 级链
f1();

案例 2:

 var a = 1;
 function fn1(){
    var a = 2;
    var b = '22';
    fn2();
    function fn2(){
       var a = 3;
       fn3();
       function fn3(){
          var a = 4;
          console.log(a);   //4
          console.log(b);   //22
        }
    }
  }
 fn1();     

二、预解析

.1 问

 console.log(num) //num is not defined

.2 问

console.log(num) //undefined   坑 1
var num = 10; 
~ // 相当于执行了以下代码 
var num;
console.log(num);  // 只申明不赋值  所以输入就是 undefined
num = 10;

.3 问(间接函数申明 利用关键字来进行申明)

function fn(){console.log(11)  //11  
}
fn();

.4 问(函数表达式采纳了表达式赋值模式 这里应用 function 赋值的没方法进行函数晋升)

//fun()  // 如果放到下面调用呢   undefined  坑 2
var fun  = function(){console.log(22) //22  
}
fun() 
~// 相当于执行了以下代码 
var fun;     // 只申明不赋
fun();      // 没有这个函数调用必定会报错  所以正确写法是将 fun 写到前面
fun = function(){   // 函数表达式
  console.log(22) //22  
}
fun(); 

1. 什么是预解析

js 代码是由浏览器中的 js 解析器来执行的,js 解析器在运行 js 代码的时候分为俩步:预解析和代码执行

1.1. 预解析:js 引擎会把 js 外面所有的 var 还有 function 晋升到以后作用域的最后面

1.2. 代码执行:依照代码的书写程序从上往下执行

2. 预解析分为 变量预解析(变量晋升)和 函数预解析(函数晋升)

2.1. 变量晋升 就是把所有的变量申明晋升到以后的作用域最后面 不晋升赋值操作

2.1. 函数晋升 就是把所有的函数申明晋升到以后作用域的最后面 不调用函数(函数表达式 调用必须写在函数表达式上面)

正文完
 0