闭包的神奇力量:掌握这4种技巧,让你的JavaScript代码更高效

职场   2024-12-27 13:00   北京  
什么是闭包?

根据 MDN:“闭包是捆绑在一起(封闭)的函数及其周围状态(词法环境)的引用的组合。换句话说,闭包使您可以从内部函数访问外部函数的作用域。在 JavaScript 中,每次创建函数时都会创建闭包。”

例如

const getShowName = () => {  const name = "fatfish" // name is a local variable created by getShowName
return () => { console.log(name) // use variable declared in the parent function }}
const showName = getShowName()
showName() // fatfish

作为前端开发工程师,我们在很多场景中都会用到它,它的功能确实很强大。

1. 解决循环中的问题

for (var i = 0; i < 3; i++) {  setTimeout(() => {    console.log(i) // What will i print out?  }, 1000 * i)}

我们怎样才能让它打印0、1、2呢?

是的,你可以使用闭包来解决这个问题。它很快就会打印出 0、1 和 2。

for (var i = 0; i < 3; i++) {  ((n) => {    setTimeout(() => {      console.log(n) // What will i print out?    }, 1000 * n)  })(i)}

当然,我们还有另一种更简单的方法,只需将var替换为let即可解决这个问题。

for (let i = 0; i < 3; i++) {  setTimeout(() => {    console.log(i) // What will i print out?  }, 1000 * i)}

2.记忆功能

利用闭包的特性,我们可以减少计算量,提高我们编写的程序的性能。

const memoize = (callback) => {  const cache = new Map()
return function (n) { if (cache.has(n)) { // When it already exists in the cache, the result will be returned directly, we don't need to calculate it again return cache.get(n) } else { const res = callback.call(this, n) cache.set(n, res) // After the first calculation, the result will be cached return res } }}const fibonacci = memoize(function fib (n) { if (n === 1) { return 1 } if (n === 2 || n === 3) { return 2 } return fib(n - 1) + fib(n - 2)})
console.log(fibonacci(1)) // 1console.log(fibonacci(10)) // 68console.log(fibonacci(10)) // 68 Read from cache instead of computing again

3. 封装私有变量和属性

很早以前,我们经常通过闭包来实现对私有变量的保护。

我们只能通过getName和setName来获取和设置_name的值。

这样我们就可以有效防止_name被恶意修改。

const createName = (name) => {  let _name = name
return { getName () { return _name }, setName (name) { _name = name } }}const p = createName('fatfish')p.getName() // fatfishp.setName('medium')p.getName() // medium

4.函数柯里化

作为一名前端开发工程师,我相信你已经了解了什么是函数柯里化。让我们尝试使用闭包来实现它。

const curry = (callback, ...args) => {  return function (...innerArgs) {    innerArgs = args.concat(innerArgs)
if (innerArgs.length >= callback.length) { return callback.apply(this, innerArgs) } else { return curry(callback, innerArgs) } }}
const add = curry((a, b, c) => { return a + b + c}, 1)console.log(add(2, 3)) // 6

4种关于的闭包的技巧我们说完了, 你还知道其他的什么方法吗?


推荐一个受到超多好评的终生学习小程序「千锋学习站」

全网超火的课程资源:涵盖18个IT行业热门课程,3000G精品授课视频,从入门到精通,理论+实战,小白适用!
全网超牛的公开课:定期邀请一线大厂大佬来直播间宣讲,全程干货,福利满满,从基础理论到实战案例,分享实战IT技能,拒绝纸上谈兵!
全网超全的题库资源:1800个知识点练习,10万道面试真题,沉浸式刷题练习,帮助各位同学夯实基础,提升技术水平,为升职加薪保驾护航!
— 不负每份期待,继续与你共同成长—
点击下方小卡片,开始学习吧
👇👇👇

End -

想要获得技能提升和职业发展
点击即可学习免费好课哦!
 
 
免费好课推荐:
 Linux云计算 | Java开发 | 鸿蒙 | Python数据分析 | 物联网 | 网络安全 | 游戏原画 | 软件测试 | Unity游戏 | PMP项目管理 | HTML5大前端 | 全媒体运营 | UI/UE设计 | 影视剪辑 | C++ | 大数据 | 计算机二级


大前端私房菜
每天推出前端开发技巧、工具资源、项目实战等主题内容。在这里,你可以找到前端性能优化的私房秘籍,JavaScript 个性化框架的私房推荐,也有过时技术的私房警示。期待在公众号与更多小伙伴相遇!我们一起进步,共同成长
 最新文章