漯河网站超市建设,网站备案流程核验单,澧县网站设计,深圳龙华观澜网站建设公司目录1、什么是闭包#xff0c;什么是作用域1.1 变量作用域1.2 闭包是啥#xff1f;如何改变变量调用格局1.3 闭包的特性2、怎么用闭包#xff0c;闭包实例应用2.1 常见闭包实例2.2 闭包异步函数的应用2.3 柯里化的应用3、闭包的优缺点3.1 优点3.2 缺点4、片尾彩蛋【写在前面…
目录1、什么是闭包什么是作用域1.1 变量作用域1.2 闭包是啥如何改变变量调用格局1.3 闭包的特性2、怎么用闭包闭包实例应用2.1 常见闭包实例2.2 闭包异步函数的应用2.3 柯里化的应用3、闭包的优缺点3.1 优点3.2 缺点4、片尾彩蛋【写在前面】2023年确实想整理好一些前端的学习心得另外也秉着不让后学习者少走弯路的原则博主是日夜挑灯阅尽千篇才整理出来的闭包一直是面试高频词汇也是很多高级应用必不可缺的下面务必给我三分钟让我为您详细解答一下闭包的前世今生。希望能给您带来帮助。 涉及知识点变量作用域闭包垃圾回收机制,立即执行函数闭包异步函数柯里化
1、什么是闭包什么是作用域
1.1 变量作用域
闭包理解的前提是我们应该先去理解变量作用域正常也无外乎全局变量和局部变量 全局变量能被所有的函数应用局部变量的话只能在声明区域应用。 好比如下所示的函数
var hdd 黄大大;
function hddFunc(){
var kf 黄小小;console.log(hdd好帅);
}
function kongfu(){console.log(kf好丑);
}
hddFunc(); //输出黄大大好帅
kongfu(); //输出报错VM138:7 Uncaught ReferenceError kf is not defined从上面的实例我们不难发现全局变量谁都能动局部变量只能在自己地盘使用。
1.2 闭包是啥如何改变变量调用格局
要是我函数体内就要用外部的变量呢也不是不可以接下来看下面这个实例
var hdd 黄大大;
function hddFunc(){
var kf 黄小小;console.log(hdd好帅);
function kongfu(){console.log(kf好丑);
}
}
hddFunc(); //输出黄大大好帅
kongfu(); //输出报错VM138:7 Uncaught ReferenceError kf is not defined输出结果还是一样的。那么我将kongfu()调用放在hddFunc()体内呢如下所示调整
var hdd 黄大大;
function hddFunc(){
var kf 黄小小;console.log(hdd好帅);
function kongfu(){console.log(kf好丑);
}
kongfu();
}
hddFunc();
//输出黄大大好帅
//输出黄小小好丑从这个实例不难发现只有在变量声明区内调用才有效也确实是实现了kongfu()函数输出了非自身区域内变量的值。其实到这里我就讲完了闭包。 总之一句话 闭包就是指内部函数有权访问到外层函数的作用域能读取到外层函数作用域声明的变量或者我们可以将变量kf和函数kongfu()之间的环境桥梁叫做闭包特别要注意的是必须得在父函数内调用。
1.3 闭包的特性
从上面我们可以特别清楚的看的出来首先是函数内声明函数其次是函数内部调用外部参数再者就是回收机制。 其实在上面的函数调用过程中hddFunc函数体内声明的变量kf因为有kongfu()函数的使用所以永远不会销毁正常函数体内的局部变量会随着函数执行完成后而销毁。因此在这里我总结一下闭包三大特性
函数嵌套函数函数内部可调用外层函数声明的变量和参数闭包机制下的参数和变量是不会被垃圾回收机制回收销毁
2、怎么用闭包闭包实例应用
2.1 常见闭包实例
function hdd() {var sq 1 function haoshuai() { return sq}return haoshuai
}
var hddhs hdd();
console.log(hddhs());
//输出 2
function hdd() {var sq 1 function haoshuai() { return sq}return haoshuai
}
var hddhs hdd();
hddhs();
console.log(hddhs());
//输出3小记从这里不难发现帅气值变量sq始终都是在的调用一次就会存储一次加一从这里就可以确定sq这个变量一直没有被回收。
2.2 闭包异步函数的应用
先用实例和大家介绍一下
for (var i 1; i 5; i) {setTimeout(function () {console.log(i-黄大大好帅);}, 50);
}
//输出:
5-黄大大好帅
5-黄大大好帅
5-黄大大好帅
5-黄大大好帅但是我就是想让他在遍历里面按照正常顺序来输出。这个时候我们可以用到闭包的概念。我们创建了一个立即执行函数将变量i放在立即执行函数内其实也就相当于这里的i被setTimeout异步函数给引用了从而实现i变量叠加后会保存原有的值。也验证了一点特性函数嵌套函数的说法
for (var i 1; i 5; i) {(function(i){setTimeout(function () {console.log(i-黄大大好帅);}, 50);})(i)
}
//输出
1-黄大大好帅
2-黄大大好帅
3-黄大大好帅
4-黄大大好帅其实最推崇的应该是下面这个方式将变量i用let进行声明因为let所声明的变量只在let命令所在的代码块内有效。如下所示
for (let i 1; i 5; i) { setTimeout(function () {console.log(i、黄大大好帅);}, 50);
}
//输出
1-黄大大好帅
2-黄大大好帅
3-黄大大好帅
4-黄大大好帅2.3 柯里化的应用
柯里化是函数的一种高阶技术我们可以理解为函数的一种转换如下
//求和函数
function sum(a, b,c) { return a bc; }
//柯里化辅助函数curry()
//curry函数的实现(不知道多少入参所以用了递归)
function curry(fn,arr[]){let len fn.length; //函数的长度是函数形参的个数return function (...args){let arrs [...arr,...args];if(arrs.length len){return curry.call(this,fn,arrs);}else{return fn(...arrs);}}}
let getSum curry(sum);
console.log(getSum(1,2,3)) //輸出6
console.log(getSum(1)(2,3)) //輸出6
console.log(getSum(1)(2)(3)) //輸出6我们不难发现里面函数嵌套函数且应用函数体外的变量。
3、闭包的优缺点
3.1 优点
1.能读取函数外层的变量从而避免全局变量被污染 2.外层变量会一直存在内存中函数结束后不会被回收机制回收
3.2 缺点
1.正因为不被回收机制所以会导致内存消耗过大伸直引发溢出所以慎用哦
4、片尾彩蛋
如果觉得这篇文章对您有帮助的话想支持博主的可以上皇榜看看哟皇榜点击此处进入