老司機帶你徹底搞懂JS閉包各種坑
老司機帶你徹底搞懂JS閉包各種坑
##閉包是js發展慣用的技巧,什麼是閉包?
function outer() { var a = '变量1' var inner = function () { console.info(a) } return inner // inner 就是一个闭包函数,因为他能够访问到outer函数的作用域 }
#從堆疊的角度看待js函數
基本變量的值一般都是存在棧記憶體中,而物件類型的變數的值儲存在堆疊記憶體中,棧記憶體儲存對應空間位址。基本的資料型態: Number 、Boolean、Undefined、String、Null。var a = 1 //a是一个基本类型 var b = {m: 20 } //b是一个对象
var a = 1; function fn(){ var b = 2; function fn1(){ console.log(b); } fn1(); } fn();
function outer() { var a = '变量1' var inner = function () { console.info(a) } return inner // inner 就是一个闭包函数,因为他能够访问到outer函数的作用域 } var inner = outer() // 获得inner闭包函数 inner() //"变量1"
坑點1: 引用的變數可能改變
function outer() { var result = []; for (var i = 0; i<10; i++){ result.[i] = function () { console.info(i) } } return result }
function outer() { var result = []; for (var i = 0; i<10; i++){ result.[i] = function (num) { return function() { console.info(num); // 此时访问的num,是上层函数执行环境的num,数组有10个函数对象,每个对象的执行环境下的number都不一样 } }(i) } return result }
坑點2: this指向問題
var object = { name: ''object", getName: function() { return function() { console.info(this.name) } } } object.getName()() // underfined // 因为里面的闭包函数是在window作用域下执行的,也就是说,this指向window
坑點3:記憶體外洩問題
function showId() { var el = document.getElementById("app") el.onclick = function(){ aler(el.id) // 这样会导致闭包引用外层的el,当执行完showId后,el无法释放 } } // 改成下面 function showId() { var el = document.getElementById("app") var id = el.id el.onclick = function(){ aler(id) // 这样会导致闭包引用外层的el,当执行完showId后,el无法释放 } el = null // 主动释放el }
#技巧1: 用閉包解決遞歸呼叫問題
function factorial(num) { if(num<= 1) { return 1; } else { return num * factorial(num-1) } } var anotherFactorial = factorial factorial = null anotherFactorial(4) // 报错 ,因为最好是return num* arguments.callee(num-1),arguments.callee指向当前执行函数,但是在严格模式下不能使用该属性也会报错,所以借助闭包来实现 // 使用闭包实现递归 function newFactorial = (function f(num){ if(num<1) {return 1} else { return num* f(num-1) } }) //这样就没有问题了,实际上起作用的是闭包函数f,而不是外面的函数newFactorial
** 技巧2:用閉包模仿區塊級作用域**
es6沒出來之前,用var定義變數存在變數提升問題,eg:for(var i=0; i<10; i++){ console.info(i) } alert(i) // 变量提升,弹出10 //为了避免i的提升可以这样做 (function () { for(var i=0; i<10; i++){ console.info(i) } })() alert(i) // underfined 因为i随着闭包函数的退出,执行环境销毁,变量回收
JavaScript影片教學專欄!
以上是老司機帶你徹底搞懂JS閉包各種坑的詳細內容。更多資訊請關注PHP中文網其他相關文章!

熱AI工具

Undresser.AI Undress
人工智慧驅動的應用程序,用於創建逼真的裸體照片

AI Clothes Remover
用於從照片中去除衣服的線上人工智慧工具。

Undress AI Tool
免費脫衣圖片

Clothoff.io
AI脫衣器

AI Hentai Generator
免費產生 AI 無盡。

熱門文章

熱工具

記事本++7.3.1
好用且免費的程式碼編輯器

SublimeText3漢化版
中文版,非常好用

禪工作室 13.0.1
強大的PHP整合開發環境

Dreamweaver CS6
視覺化網頁開發工具

SublimeText3 Mac版
神級程式碼編輯軟體(SublimeText3)

熱門話題

人臉偵測辨識技術已經是一個比較成熟且應用廣泛的技術。而目前最廣泛的網路應用語言非JS莫屬,在Web前端實現人臉偵測辨識相比後端的人臉辨識有優勢也有弱勢。優點包括減少網路互動、即時識別,大大縮短了使用者等待時間,提高了使用者體驗;弱勢是:受到模型大小限制,其中準確率也有限。如何在web端使用js實現人臉偵測呢?為了實現Web端人臉識別,需要熟悉相關的程式語言和技術,如JavaScript、HTML、CSS、WebRTC等。同時也需要掌握相關的電腦視覺和人工智慧技術。值得注意的是,由於Web端的計

在C++中,閉包是能夠存取外部變數的lambda表達式。若要建立閉包,請擷取lambda表達式中的外部變數。閉包提供可重複使用性、資訊隱藏和延遲求值等優點。它們在事件處理程序等實際情況中很有用,其中即使外部變數被銷毀,閉包仍然可以存取它們。

C++Lambda表達式支援閉包,即保存函數作用域變數並供函數存取。語法為[capture-list](parameters)->return-type{function-body}。 capture-list定義要捕獲的變量,可以使用[=]按值捕獲所有局部變量,[&]按引用捕獲所有局部變量,或[variable1,variable2,...]捕獲特定變量。 Lambda表達式只能存取捕獲的變量,但無法修改原始值。

閉包是一種巢狀函數,它能存取外層函數作用域的變量,優點包括資料封裝、狀態保持和靈活性。缺點包括記憶體消耗、效能影響和調試複雜性。此外,閉包還可以建立匿名函數,並將其作為回調或參數傳遞給其他函數。

標題:閉包造成的記憶體洩漏及解決方法引言:閉包是JavaScript中一個非常常見的概念,它可以讓內部函數存取外部函數的變數。然而,閉包在使用不當的情況下可能導致記憶體洩漏。本文將探討閉包所造成的記憶體洩漏問題,並提供解決方法及具體程式碼範例。一、閉包引起的記憶體洩漏問題閉包的特性是內部函數可以存取外部函數的變量,這意味著在閉包中引用的變數不會被垃圾回收。如果使用不當,

函數指針和閉包對Go性能的影響如下:函數指針:稍慢於直接調用,但可提高可讀性和可復用性。閉包:通常更慢,但可封裝資料和行為。實戰案例:函數指標可最佳化排序演算法,閉包可建立事件處理程序,但會帶來效能損失。

js和vue的關係:1、JS作為Web開發基石;2、Vue.js作為前端框架的崛起;3、JS與Vue的互補關係;4、JS與Vue的實踐應用。

是的,可以透過鍊式呼叫和閉包優化程式碼簡潔性和可讀性:鍊式呼叫可將函數呼叫連結為一個流暢介面。閉包可建立可重複使用程式碼區塊,並在函數外部存取變數。
