JS 【详解】作用域

简介: JS 【详解】作用域

作用域即变量/函数可以被访问的区域。

全局作用域

{} 和函数外的区域为全局作用域。

  • 全局作用域中的声明的变量是全局变量,在页面的任意的部分都可以访问。
  • 全局作用域中无法访问函数作用域的变量
  • 全局作用域在页面打开时创建,在页面关闭时销毁。
  • 全局作用域中有一个全局对象window,它代表的是一个浏览器的窗口,由浏览器创建,可以直接使用,全局变量是window对象的属性,函数是window对象的方法。
function foo() {
    var a = b = 100; // 连续赋值
}

foo();

console.log(window.b); // 打印 100 
console.log(window.a); // 打印 undefined 
console.log(a); // 报错 Uncaught ReferenceError: a is not defined

var a = b = 100 这行连续赋值的代码等价于 var a = (b = 100),其执行顺序是:

  1. 先把 100 赋值给 b;
  2. 再声明变量 a
  3. 再把 b 的值赋值给 a
  • b 是未经声明的变量就被赋值了,属于 window.b;
  • a 的作用域仅限于 foo() 函数内部,不属于 window;

块作用域

{} 中为块作用域

  • 变量只在代码块中有效;

ES5本身不提供块级作用域,通常使用立即调用函数表达式实现

(function () {
  var block_scoped=0;
}());
console.log(block_scoped); //引用错误

ES6中,使用 let 和 const 实现块级作用域

let a =1
if(a===1) {
  let b = 2
}
console.log(b); // Uncaught ReferenceError: b is not defined

函数作用域

函数内的区域为函数作用域(即 function 中 { } 内的部分)

函数作用域的原理

执行期上下文:当函数执行时,会创建一个执行期上下文的内部对象。每调用一次函数,就会创建一个新的上下文对象,他们之间是相互独立的。当函数执行完毕,它所产生的执行期上下文会被销毁。


在函数作用域操作一个变量时,它会先在自身作用域中寻找,如果有就直接使用(就近原则)。如果没有则向上一级作用域中寻找,直到找到全局作用域;如果全局作用域中依然没有找到,则会报错ReferenceError。

函数作用域的特点

  • 函数作用域中可以访问到全局作用域的变量,如window.a(全局作用域和函数作用域都定义了变量a时)
  • 全局作用域无法访问函数内定义的变量
  • 函数中,使用var关键字声明的变量,会在函数中所有的代码执行之前被声明
  • 函数中,没有var声明的变量都是全局变量,而且并不会提前声明。
  • 函数中,函数声明也会在函数中所有的代码执行之前执行
    var a = 1;

    function foo() {
        console.log(a);
        a = 2;     // 此处的a相当于window.a
    }

    foo(); // 打印结果是1
    console.log(a);   //打印结果是2

定义形参就相当于在函数作用域中声明了变量。

    function fun6(e) { // 这个函数中,因为有了形参 e,此时就相当于在函数内部的第一行代码里,写了 var e;
        console.log(e);
    }

    fun6();  //打印结果为 undefined
    fun6(123);//打印结果为123

模块作用域

ES6新增语法,每个js文件都是一个模块,每个模块中的区域即模块作用域,其他文件要使用模块中的变量/函数,必须对外导出模块中的变量/函数,并在目标文件中引入。

图解—JS调用栈

目录
相关文章
|
9天前
|
JavaScript 前端开发 开发者
JavaScript的变量提升是一种编译阶段的行为,它将`var`声明的变量和函数声明移至作用域顶部。
【6月更文挑战第27天】JavaScript的变量提升是一种编译阶段的行为,它将`var`声明的变量和函数声明移至作用域顶部。变量默认值为`undefined`,函数则整体提升。`let`和`const`不在提升范围内,存在暂时性死区。现代实践推荐明确声明位置以减少误解。
15 2
|
15天前
|
存储 JavaScript 前端开发
第五篇-Javascript作用域
第五篇-Javascript作用域
17 2
|
18天前
|
JavaScript 前端开发
JavaScript 作用域
JavaScript 作用域
15 2
|
2月前
|
JavaScript 前端开发
JavaScript 闭包:让你更深入了解函数和作用域
JavaScript 闭包:让你更深入了解函数和作用域
|
11天前
|
自然语言处理 JavaScript 前端开发
JavaScript闭包是函数访问外部作用域变量的能力体现,它用于封装私有变量、持久化状态、避免全局污染和处理异步操作。
【6月更文挑战第25天】JavaScript闭包是函数访问外部作用域变量的能力体现,它用于封装私有变量、持久化状态、避免全局污染和处理异步操作。闭包基于作用域链和垃圾回收机制,允许函数记住其定义时的环境。例如,`createCounter`函数返回的内部函数能访问并更新`count`,每次调用`counter()`计数器递增,展示了闭包维持状态的特性。
26 5
|
9天前
|
JavaScript 前端开发
JavaScript作用域关乎变量和函数的可见范围。
【6月更文挑战第27天】JavaScript作用域关乎变量和函数的可见范围。全局作用域适用于整个脚本,局部作用域限于函数内部,而ES6引入的`let`和`const`实现了块级作用域。全局变量易引发冲突和内存占用,局部作用域在函数执行后消失,块级作用域提高了变量管理的灵活性。作用域关键在于组织代码和管理变量生命周期。
17 1
|
11天前
|
JavaScript 前端开发
JavaScript中的变量提升(Hoisting)将`var`声明和函数声明提前到作用域顶部,允许在声明前使用
【6月更文挑战第25天】JavaScript中的变量提升(Hoisting)将`var`声明和函数声明提前到作用域顶部,允许在声明前使用。`let`和`const`不完全提升,存在暂时性死区(TDZ),尝试在初始化前访问会出错。函数声明会被提升,但函数表达式不会。
17 3
|
17天前
|
JavaScript
Vue.js中使用.self修饰符来限制事件处理程序的作用域
Vue.js中使用.self修饰符来限制事件处理程序的作用域
|
19天前
|
自然语言处理 JavaScript 前端开发
【JavaScript】JavaScript基础知识强化:变量提升、作用域逻辑及TDZ的全面解析
【JavaScript】JavaScript基础知识强化:变量提升、作用域逻辑及TDZ的全面解析
19 3
|
22天前
|
自然语言处理 JavaScript 前端开发
深入了解JS作用域
深入了解JS作用域