javaScript学习笔记31day————闭包

本文深入探讨了JavaScript中的闭包概念,包括其特点和作用。闭包允许函数访问和存储外部作用域的变量,防止被垃圾回收机制清除。通过示例展示了闭包如何在函数嵌套和变量持久化中的应用,以及在解决循环中变量共享问题和定时器场景下的重要作用。
摘要由CSDN通过智能技术生成

一、闭包的概念:

能够访问另一个函数的变量,和储存数据的函数。

在之前我们学到,javaScript作用域分为局部作用域和全局作用域;

基于我们所熟悉的作用域链相关知识,我们知道在js作用域环境中,访问变量的权利是由内向外

内层作用域可以访问当前作用域下的变量,并且可以向外访问到包含当前作用于的外层作用域下的变量。

外层作用域可以访问当前作用域下的变量,但是不可访问到当前作用域下包含的内层作用域的变量。同样,在不同作用域中也是不能互相访问彼此的变量的。

//局部作用域
function fun(){
    var a = 1;
    console.log(a);//1
  
}
console.log(a);//a is not defind


//全局作用域
var b = 1
function fun(){
    var a = 1;
    console.log(a);//1
    console.log(b);//1
}
console.log(a);//a is not defind
fun()
console.log(b);//1

二、闭包的特点: 

  1. 函数嵌套函数
  2. 可以在一个函数外部访问函数内部的变量
  3. 参数和变量不会被垃圾回收机制回收

    function fun(){
            var num = 10;
            return function(){
                num++;
            }
        }
        fun();//ƒ (){num++;}




        function demo() {
            let a = 1;
            return function () {
                return a;
            }
        }
        let b = demo();
        console.log(b()); // 1

在这段代码中,demo()中的返回值是一个匿名函数,这个函数在demo()作用域内部,所以它可以获取demo()作用域下变量a的值,将这个值作为返回值赋给全局作用域下的变量b,实现了在全局变量下获取到局部变量中的变量的值。 

闭包函数变量的意义:

1、fun()开启一个函数执行空间 并把这个函数执行空间结果返回res

2、res是全局变量 这个变量是不会被销毁的

3、res的值不能被销毁

4、res的值依赖fun()这个函数执行,所以fun函数执行空间也不能被销毁

5、fun()函数执行空间不能被销毁,所以fun函数执行空间也不能被销毁

6、让变量始终保持在内存中

        function fun(){
            var num =10;
            console.log(num);//10
            return function(){
                num++;
                console.log(num);//无返回值
            }
        }
        let res = fun()
        res()//11
        res()//12
        res()//13

闭包的用途:

闭包前:

     for (var i = 0; i < btns.length; i++) {
        //    console.log(btns[i]);
        btns[i].onclick = (function (n) {
            
            // n 就是函数中的局部变量
            // 就是把这个函数返回给每一个元素的点击事件
            return function () {
                // i 的值 始终都为4
                // 事件驱动程序
                document.querySelector(".active").classList.remove("active");
                this.classList.add("active");
                // 显示对应的li 那么需要获取点击这个元素的索引值
                // console.log(n);
                document.querySelector('.show').classList.remove('show');
                // lis[n].style.display = 'block';
                lis[n].classList.add('show');
                console.log(lis[n]);
            };
        })(i);
        // i 就是给 n赋值
    }

闭包后:闭包后的代码简单易懂

for (let i = 0; i < btns.length; i++) { btns[i].onmouseover=function () { console.log(i);
    document.querySelector(".active").classList.remove("active"); this.classList.add("active");
    document.querySelector('.show').classList.remove('show'); lis[i].classList.add('show'); }; }

经典例子:闭包定时器

1、当变量为全局变量时

        for (var i = 0; i < 5; ++i) {//全部变量的时候
            setTimeout(function () {
                console.log(i);
            }, 1000)
        }

结果:

2、当变量为局部变量时:

        for (let i = 0; i < 5; ++i){
            setTimeout(function(){
                console.log(i);
            }, 1000)
        }

 上面代码中,我们引入闭包来保存变量i,将setTimeout放入立即执行函数中,将for循环中的循环值i作为参数传递,1000毫秒后同时打印出0 1 2 3 4

        for (var i = 0; i < 5; i++){
            (function(i){
                setTimeout(function(){
                    console.log(i);
                }, i*500);
            })(i);
        }

结果:

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值