Javascript的独特的概念之闭包(js 闭包的作用)一篇读懂

随心笔谈2年前发布 admin
202 0 0

文章摘要

JavaScript中的闭包(closure)是一种独特的概念,它是C++、Java等语言中没有的。闭包的核心在于它能够通过返回函数(或引用函数)来维护内部变量的引用,从而实现复杂的变量管理功能。 闭包的作用域与强类型语言(如C++、Java)不同。在JavaScript中,函数内部可以直接访问全局变量,但在函数外部无法访问函数内的局部变量。为了访问这些局部变量,需要使用闭包。例如,通过定义一个返回函数(如`fun3`)的方式,可以在外部引用内部变量(如`x`)。 闭包的另一个重要作用是可以保存变量的引用。即使函数执行完毕,闭包的引用仍然有效。例如,在`fun_test`函数中,`fun_common`函数在`fun1`和`fun2`中被定义,但由于它们被闭包捕获,可以在外部分别引用并执行。 此外,闭包还可以帮助净化命名空间,缓解命名空间冲突的问题。通过将内部函数和变量通过闭包引用到外部,可以避免同名变量的冲突。 总体而言,闭包是JavaScript中一种强大的机制,能够提升代码的可维护性和扩展性。



目录Javascript闭包简介:为什么是闭包:总结

Javascript语言中,有一个独特的概念:闭包(closure),这在类似C++,Java等编程语言中没有这个概念。很多高级应用都要依靠闭包实现。

或者说,为什么需要闭包,闭包的作用到底是什么?要理解这个概念,首先要理解Javascript中的作用域。

闭包的作用域:

和Java,C/C++等高级编程语言一样,Javascript也有作用域这个概念。但是,相比而言,它们有很大的区别。

1). 变量的标识:Java,C/C++等编程语言是强类型语言,即变量的声明需要用类型来标识(无论是普通类型,还是自定义类型)。

而Javascript语言是弱类型语言,即不需要用具体的类型来标识变量(例如,只需要用var/let,或者都不需要用它们来标识)。

2). 变量的作用域:

Javascript:函数内部可以直接读取全局变量;在函数外部无法访问函数内的局部变量。

函数内部声明的变量,一定要用var来标识;如果一个变量没有标识,则这个变量实际上是一个全局变量。

例如:

var x=10;
  function fun1(){
var y=20;
z=30;
    console.log(x); //success
  }
fun1()
//console.log(y); //error:Uncaught ReferenceError: y is not defined。
//分析:y是fun1的内部变量,在函数外部方法fun1的内部变量y
console.log(z); //success:z实际上是全局变量

运行结果:

10

30

10 

闭包的概念以及使用:

可以将闭包理解为: 一个拥有许多变量和绑定了这些变量的环境的表达式(通常是一个函数),因而这些变量也是该表达式的一部分。

例如:

function fun2(){
   var x=100;
   function fun3(){
     console.log(x);
   }
   return fun3;
 }
 var result=fun2();
 result(); //success,输出100

这就是一个闭包的例子。fun2函数的返回值赋给result,再执行result(),从而访问到fun2中的fun3函数的代码。 

有时,我们需要能够访问到函数内的局部变量,这时,就需要用闭包来实现。例如,

function fun4(){
    var x=100;
iAddOne=function(){
x=x*x;
}
    function fun_41(){
      console.log(x);
    }
    return fun_41;
  }
  var res=fun4();
res(); // 10
iAddOne();
res(); // 11

运行结果:

100

10000

可见,这里,闭包是一个函数。

闭包的另外一个作用是:

让闭包表达式的变量始终保存在内存中。因为“变量也是该表达式的一部分”,所以,在函数外部拥有来这个闭包表达式,就相当于拥有来表达式中的变量。

只有在”拥有表达式的函数“的生命周期结束,闭包的生命周期也随之结束。

闭包还可以净化命名空间。

Javascript的一大糟粕就是命名空间冲突。

在C++中,使用using namespace 来进行命名空间的声明和使用;

在java语言中,用import packagename来进行区别。

而在Javascript中,却没有这样的机制。这样,很容易引起类似“同名方法的多处定义和引用”而带来的问题。

因此,有了闭包,在某种程度上,可以减缓这类问题。即内部函数名称相同,但是外部函数可以不同名字就行。

例如:

function fun_test() {
function fun1(){
   var x=100;
   function fun_common(){
     console.log(x);
   }
   return fun_common;
 }
function fun2(){
   var y=200;
   function fun_common(){
     console.log(y);
   }
   return fun_common;
 }
var result1=fun1();
result1(); //success,输出100
var result2=fun2();
result2(); //success,输出200
}

运行结果:

100

200

 

可见, fun_common分别在fun1和fun2函数中有定义,在fun_test中可以正确访问到它们。

本篇文章就到这里了,希望能够给你带来帮助,也希望您能够多多关注脚本之家的更多内容!  

vv

您可能感兴趣的文章:一文剖析JavaScript中闭包的难点JavaScript深入理解作用域链与闭包详情js中闭包结合递归等于柯里化原理解析JavaScript内存管理与闭包实例详解学习JavaScript中的闭包closure应该注意什么JavaScript?中的作用域与闭包一文详解JavaScript闭包典型应用你真的了解JavaScript的作用域与闭包吗JavaScript闭包原理与使用介绍

© 版权声明

相关文章