LOGO OA教程 ERP教程 模切知識交流 PMS教程 CRM教程 開發文檔 其他文檔  
 
網站管理員

天使還是魔鬼?6年老司機帶你玩轉js閉包

freeflydom
2025年6月6日 9:18 本文熱度 66

一、閉包是什么?一個簡單的例子

function outer() {
    let me = '小楊';
    return function inner() {
        console.log(`大家好,我是${me}`);
    };
}
const sayHello = outer();
sayHello(); // "大家好,我是小楊"

看到沒?inner函數記住了outer函數的me變量,這就是閉包!

二、閉包的三大妙用(天使面)

1. 創建私有變量

function createCounter() {
    let count = 0;
    return {
        increment() { count++ },
        getCount() { return count }
    };
}
const counter = createCounter();
counter.increment();
console.log(counter.getCount()); // 1
console.log(counter.count); // undefined

2. 實現函數柯里化

function multiply(a) {
    return function(b) {
        return a * b;
    };
}
const double = multiply(2);
console.log(double(5)); // 10

3. 事件處理中的妙用

function setupButtons() {
    for(var i = 1; i <= 3; i++) {
        (function(index) {
            document.getElementById(`btn-${index}`)
                .addEventListener('click', function() {
                    console.log(`我是按鈕${index}`);
                });
        })(i);
    }
}

三、閉包的三大坑(魔鬼面)

1. 內存泄漏

function leakMemory() {
    const bigData = new Array(1000000).fill('*');
    return function() {
        console.log('我還記得bigData');
    };
}
const leaked = leakMemory();
// bigData本應該被回收,但閉包讓它一直存在

2. 性能問題

function slowPerformance() {
    const data = {}; // 大對象
    return function(key, value) {
        data[key] = value;
        // 每次調用都要訪問閉包變量
    };
}

3. 意外的變量共享

function createFunctions() {
    let funcs = [];
    for(var i = 0; i < 3; i++) {
        funcs.push(function() {
            console.log(i); // 全是3!
        });
    }
    return funcs;
}

四、閉包優化六大法則(6年經驗總結)

1. 及時釋放引用

function createHeavyObject() {
    const heavy = new Array(1000000).fill('*');
    return {
        useHeavy: function() {
            // 使用heavy
        },
        cleanup: function() {
            heavy = null; // 手動釋放
        }
    };
}

2. 使用塊級作用域

// 修復前面的共享變量問題
function createFixedFunctions() {
    let funcs = [];
    for(let i = 0; i < 3; i++) { // 使用let
        funcs.push(function() {
            console.log(i); // 0,1,2
        });
    }
    return funcs;
}

3. 避免不必要的閉包

// 不好的寫法
function unneededClosure() {
    const data = {};
    return function() {
        // 根本不使用data,卻形成了閉包
        console.log('Hello');
    };
}
// 好的寫法
function noClosure() {
    console.log('Hello');
}

4. 使用WeakMap管理私有變量

const privateData = new WeakMap();
class MyClass {
    constructor() {
        privateData.set(this, {
            secret: '我是私有數據'
        });
    }
    
    getSecret() {
        return privateData.get(this).secret;
    }
}

5. 合理使用IIFE

// 立即執行函數減少閉包生命周期
(function() {
    const tempData = processData();
    // 使用tempData
})(); // 執行完立即釋放

6. 使用模塊化

// 模塊化天然適合管理閉包
const counterModule = (function() {
    let count = 0;
    
    return {
        increment() { count++ },
        getCount() { return count }
    };
})();

五、真實案例分享

案例1:我曾經在項目中遇到一個頁面卡頓問題,最后發現是因為一個事件處理函數形成了閉包,持有了一個大DOM樹的引用。解決方案是:

// 修復前
function setup() {
    const bigElement = document.getElementById('big');
    button.addEventListener('click', function() {
        // 持有bigElement引用
        console.log(bigElement.id);
    });
}
// 修復后
function setup() {
    const id = 'big';
    button.addEventListener('click', function() {
        // 只存儲需要的id
        console.log(id);
    });
}

六、總結

閉包就像一把雙刃劍:
? 優點:實現私有變量、函數柯里化、模塊化等
? 缺點:可能導致內存泄漏、性能問題

記住我的6年經驗總結:

  1. 及時釋放不再需要的引用
  2. 優先使用塊級作用域
  3. 避免不必要的閉包
  4. 合理使用WeakMap和模塊化
  5. 善用開發者工具檢查內存

轉自https://juejin.cn/post/7512259761196957707


該文章在 2025/6/6 9:18:57 編輯過
關鍵字查詢
相關文章
正在查詢...
點晴ERP是一款針對中小制造業的專業生產管理軟件系統,系統成熟度和易用性得到了國內大量中小企業的青睞。
點晴PMS碼頭管理系統主要針對港口碼頭集裝箱與散貨日常運作、調度、堆場、車隊、財務費用、相關報表等業務管理,結合碼頭的業務特點,圍繞調度、堆場作業而開發的。集技術的先進性、管理的有效性于一體,是物流碼頭及其他港口類企業的高效ERP管理信息系統。
點晴WMS倉儲管理系統提供了貨物產品管理,銷售管理,采購管理,倉儲管理,倉庫管理,保質期管理,貨位管理,庫位管理,生產管理,WMS管理系統,標簽打印,條形碼,二維碼管理,批號管理軟件。
點晴免費OA是一款軟件和通用服務都免費,不限功能、不限時間、不限用戶的免費OA協同辦公管理系統。
Copyright 2010-2025 ClickSun All Rights Reserved

黄频国产免费高清视频,久久不卡精品中文字幕一区,激情五月天AV电影在线观看,欧美国产韩国日本一区二区
亚洲AV日韩AV欧v在线天堂 | 亚洲精品欧美综合久久 | 亚洲欧美午夜不卡在线观看 | 亚洲狠狠丁香婷婷综合久久久 | 亚洲白色白色永久在线播放 | 亚洲午夜福利在线网 |