网站首页 > 基础教程 正文
点关注,不迷路,每天大量前端资料更新
闭包
function fn1(){ var a = 2 function fn2(){ conso1e.log(a) //fn2引用了fn1函数中的变量a,产生了闭包 } } fn1()
如何产生闭包
当一个嵌套的内部(子)函数引用了嵌套的外部(父)函数的变量(函数)就产生了闭包(满足了这个条件就是闭包),如上例子
闭包到底是什么
通过Chrome中的调试工具查看
理解一:闭包是嵌套的内部函数(绝大部分人)认为上例子中的fn2
理解二:包含在被引用变量(函数)的对象(极少数人)认为上例子的变量a
注意:闭包产生在嵌套的内部函数中
产生闭包的条件
1.函数嵌套
2.内部函数引用了外部函数的数据(变量或函数)
3.外部函数被执行(不用调用内部函数)
常见的闭包
1.将一个函数作为另一个函数的返回值
2.将函数作为实参传递给另一个函数调用
1.将一个函数作为另一个函数的返回值
function fn1(){ var a = 2 function fn2(){ a++ conso1e.log(a) } return fn2 } var f = fn1() f() //3 f() //4 f = null //在嵌套的内部函数成为垃圾对象,就是闭包死亡
2.将函数作为实参传递给另一个函数调用
function showDelay(msg,time){ setTimeout(function(){ alert(msg) },time) } showDelay('alibaba',2000)
闭包的作用
使用函数内部的变量在函数执行后,仍然存活在内存中(延长了局部变量的生命周期)
让函数外部可以操作读写到函数内部的数据
函数执行完后,函数内部声明的局部变量是否还存在?
一般不存在,在有闭包的情况下,存在,仅仅闭包中的变量在闭包中,在函数执行完后存在,别的在函数执行完后都会释放
在函数外部能直接访问函数内部的局部变量吗?
不能,但是闭包的技术可以
闭包的产生,在嵌套的内部函数定义执行完就产生了(不是在执行时)
死亡:在嵌套的内部函数成为垃圾对象,就是死亡
闭包的应用:
1.定义js模块:具有特定功能的js文件,将所有的数据和功能都封装在一个函数内部中
只向外暴露一个包含n个方法的对象或者函数,模块的使用者,只需要通过模块暴露的对象调用方法
来实现对应的功能
myModule.js如下
function myModule(){ var msg = 'alibaba' function doSomething(){ conso1e.log('doSomething()'+msg.toUpperCase()) } function doOtherthing(){ conso1e.log('doOtherthing()'+msg.toLowerCase()) } //向外暴露一个包含n个方法的对象或者函数 return{ doSomething:doSomething doOtherthing:doOtherthing } }
然后引入
<script src = 'myModule.js'></script> <script> var moulder = myModule moulder.doSomething() moulder.doOtherthing() </script>
闭包的缺点与解决方法
函数执行完后,函数内的局部变量没有释放,占用内存时间会变长
容易造成内存泄漏
function fn1(){ var arr = new Array[1000000] function fn2(){ conso1e.log(arr.length) } return fn2 } var f = fn1() f = null //解决方法
解决
能不用闭包就不用,及时释放
内存泄露与内存溢出
内存溢出
一种程序运行出现的错误
当程序运行需要的内存超过剩余的内存时,就抛出了内存溢出的错误
内存溢出
var obj = {} for (var i = 0;i<10000;i++){ obj[i] = new Array(1000000000) }
内存泄露
占用的内存没有及时释放
内存泄露积累多了就容易导致内存溢出
常见的内存泄露:
1.意外的全局变量
2.没有及时清理的计时器或回调函数
3.闭包
1.意外的全局变量
function fn(){ a = new Array(1000000) //用var来申明才对 conso1e.log(a) } fn() 在fn()执行后a并没有被释放
2.建立的定时器,必须清除
3.闭包
function fn1(){ var arr = new Array[1000000] function fn2(){ conso1e.log(arr.length) } return fn2 } var f = fn1() //没有f = null
猜你喜欢
- 2024-10-12 菜鸟面试:(Object和String)时间类和日期类以及包装类等而谈
- 2024-10-12 做前端不得不会的纯js验证码,你知道吗?
- 2024-10-12 js——prototype 属性 js object.prototype
- 2024-10-12 2024 年 5 个令人兴奋的 JavaScript 新功能
- 2024-10-12 JavaScript 基本数据类型和引用类型的区别详解
- 2024-10-12 「JS 口袋书」第 1 和 2 章:JS简介及基础
- 2024-10-12 第15节 Javascript引用类型-Web前端开发-零点程序员-王唯
- 2024-10-12 javascript系统学习(五)万物皆对象
- 2024-10-12 讲解一下JavaScript基本类型和引用类型的值
- 2024-10-12 JavaScript 原型扩展——对象(Object)
- 最近发表
- 标签列表
-
- jsp (69)
- pythonlist (60)
- gitpush (78)
- gitreset (66)
- python字典 (67)
- dockercp (63)
- gitclone命令 (63)
- dockersave (62)
- linux命令大全 (65)
- mysql教程 (60)
- pythonif (86)
- location.href (69)
- deletesql (62)
- c++模板 (62)
- linuxgzip (68)
- 字符串连接 (73)
- nginx配置文件详解 (61)
- html标签 (69)
- c++初始化列表 (64)
- mysqlinnodbmyisam区别 (63)
- arraylistadd (66)
- console.table (62)
- mysqldatesub函数 (63)
- window10java环境变量设置 (66)
- c++虚函数和纯虚函数的区别 (66)