美文网首页
JavaScript闭包

JavaScript闭包

作者: 追逐_e6cf | 来源:发表于2019-02-16 14:00 被阅读0次

一、获取局部作用域的变量

  1. 通过变量向外传递。
  2. 通过函数向外传递。
  3. 条件和循环体:{}不代表作用域,在es6语法中,{}会被看做代码块,此时在{}当中声明一个函数,相当于var声明,尽量不要在{}当中声明函数,否则调用的时候会有问题。
// 通过变量 向外传递    
var b = '';
function fn1(){
    var a = "月薪10w";
    b = a;
}
fn1();
alert(b); //取到函数内局部作用域的变量a的值

// 通过函数传参获取
function fn1(){
    var a = "月薪10w";
    fn2(a);
}
function fn2(str){
    alert(str);
}
fn1();
alert(fn1); //undefined
{
    function fn1(){
        alert(1);
    }
}   

二、闭包

  1. js垃圾回收机制:js 中的变量和函数不再使用后,会被自动js垃圾回收机制回收。
  2. 形成闭包的条件:有函数/作用域的嵌套;内部函数引用外部函数的变量/参数。
  3. 闭包的结果:内部函数的使用外部函数的那些变量和参数仍然会保存,使用return返回了此内部函数,上面的变量和参数不会被回收。
  4. 闭包的原因:返回的函数并非孤立的函数,而是连同周围的环境(AO)打了一个包,成了一个封闭的环境包,共同返回出来 ---->闭包。
  5. 我们在返回函数的时候,并不是单纯的返回了一个函数,我们把该函数连同他的AO链一起返回了。
  6. 函数的作用域,取决于声明时而不取决于调用时。
  7. 变量存储function(){}{}[]存储的是一个地址。
function t1(){
    var age = 20;
    function t2(){
        alert(age);
    }
    return t2;
}
var tmp = t1();
var age = 1000;
tmp(); //20

// win 1. AO{t1:function(){},tmp:un,age:un}
//     2. t1     1. AO{age:un,t2:fun}
//               2. AO{age:20,t2:fn}
//        AO{t1:function(){},tmp:t2,age:1000}
//      
//        tmp  t2 1.AO{}
var age = 10;
function t1(){
    var age = 20;
    return function t2(){
        alert(++age);
    }
}
var t3 = t1();
t3(); // 21
t3(); // 22
t3(); // 23
alert(age); //10
var age = 10;
function t1(){
    var age = 20;
    return function t2(){
        alert(++age);
    }
}
var t3 = t1();
var t4 = t1();
t3(); //21
t4(); //21
function foo(){
    var a = 2;
    function baz(){
        console.log(a);
    }
    bar(baz);
}
function bar(fn){
    var a = 3;
    fn();
}
foo();
//2

三、闭包计数器

使用js的命名空间,优点:变量不受污染。

<script>
    var chengming = {};//js的命名空间 一般就是这么写
    chengming.inc = (function(){
        var cnt = 0;
        return function(){
            return ++cnt;
        }
    })();

    console.log(chengming.inc());
</script>
<script>
    var cnt = 100;
    console.log(inc()); //报错,window下访问不到inc
</script>

四、循环中的闭包

<body>
    <input type="button" name="" value="按钮1">
    <input type="button" name="" value="按钮2">
    <input type="button" name="" value="按钮3">
</body>
<script>
    var inp = document.getElementsByTagName('input');
    for(var i=0; i<inp.length; i++){
        inp[i].onclick = function(){
            inp[i].style.background = "yellow";
        }
    }
    //点击按钮会报错,因为i在window全局上,for结束之后,本身的值就是3
</script>
// 方法一  用自定义属性
for(var i=0;i<inp.length;i++){
    inp[i].i = i;
    inp[i].onclick = function(){
        inp[this.i].style.background = 'yellow';
    }
}
// 方法一  用let关键字
for(let i=0; i<inp.length; i++){
    inp[i].onclick = function(){
        inp[i].style.background = "yellow";
    }
}
// 方法三 使用this
for(var i=0; i<inp.length; i++){
    inp[i].onclick = function(){
        this.style.background = "yellow";
    }
}
// 方法四  for循环每次执行,都会立即执行一个匿名函数,并且匿名函数的作用域中传入了当时的i作为参数传递
for(var i=0; i<inp.length; i++){
    (function(i){
        // AO{i:1}
        inp[i].onclick = function(){
            // AO:{}
            inp[i].style.background = 'yellow';     
        }
    })(i)
}
// 方法五
for(var i=0; i<inp.length; i++){
    (function(){
        // AO{}
        var arg = i;
        inp[arg].onclick = function(){
            // AO:{}
            inp[arg].style.background = 'yellow';
        }
    })()
}
// 方法六
for(var i=0; i<inp.length; i++){
    inp[i].onclick = function(i){
        // AO:{i:0}
        return function(){
            inp[i].style.background = 'yellow';
        }
    }(i)
}
// 方法七
for(var i=0; i<inp.length; i++){
    (inp[i].onclick = function(){
        inp[arguments.callee.i].style.background = 'yellow';
    }).i = i;
}
// 方法八九 基本包装类型
for(var i=0; i<inp.length; i++){
    inp[i].onclick = new Function(`inp[${i}].style.background = 'yellow';`);
}
for(var i=0; i<inp.length; i++){
    inp[i].onclick = Function(`inp[${i}].style.background = 'yellow';`);
}

相关文章

  • JavaScript----闭包

    javascript之闭包 闭包的概念     闭包(closure)是 JavaScript 的一种语法特性。 ...

  • 学习JavaScript闭包和作用域笔记

    JS JavaScript闭包和作用域 闭包 JavaScript高级程序设计中对闭包的定义:闭包是指有权访问另外...

  • javascript中闭包是什么

    javascript中闭包是什么 JavaScript 变量可以是局部变量或全局变量。私有变量可以用到闭包。闭包就...

  • Javascript 闭包

    闭包 (注:所以案例以 javascript 实现) 初识闭包 什么是闭包 MDNClosures are fun...

  • 作用域闭包

    概览 背景知识:JavaScript内存管理、JavaScript作用域。 内容 1 闭包定义 闭包:当函数可以记...

  • JavaScript 作用域

    概览 背景知识:JavaScript内存管理、JavaScript作用域。 内容 1 闭包定义 闭包:当函数可以记...

  • 20170815 前端开发日报

    JavaScript闭包,只学这篇就够了 闭包不是魔法 这篇文章使用一些简单的代码例子来解释JavaScript闭...

  • JavaScript深入理解-闭包(Closure)

    推荐文章:学习Javascript闭包(Closure)- 阮一峰javascript深入理解-从作用域链理解闭包...

  • 闭包

    学习Javascript闭包(Closure)

  • JS之闭包与IIFE

    本篇文章主要讨论了: JavaScript引擎 全局对象 闭包 循环 + 闭包 IIFE + 闭包 1.JavaS...

网友评论

      本文标题:JavaScript闭包

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