在最近的一個專案中,我遇到了一個函數,其效率不盡如人意。該函數執行了兩個映射循環、三個過濾器(每個過濾器都附帶一個包含)和一個帶有內建 find 的附加映射,總共 12 次迭代。雖然其中一些方法(例如過濾器)不需要遍歷整個數組,但該操作的成本仍然相當高,尤其是對於大量項目。
這個函數的複雜度是 O(n * m),隨著專案規模的擴大,這很快就會成為一個問題。
所以我決定優化這個功能。我採取的第一步是將兩個鍵數組替換為 Set。在 JavaScript 中,Set 是一種儲存唯一資料的結構,並且提供比陣列更快的存在檢查。雖然檢查陣列的複雜度為 O(n),但在 Set 中複雜度為 O(1)。此外,與 Array.includes 不同,Set.has 方法的效能不會隨著 Set 中資料數量的增加而降低。
此變更已經為在陣列上運行的濾波器提供了顯著的改進。然而,在其中一張地圖中,有一個 Array.find() 也可以優化。在 JavaScript 中,Map 是索引列表,而 Array.find 執行線性搜索,並且速度可能比 Map 慢 2,100 到 12,000 倍,具體取決於執行程式碼的處理器的效能。
透過在其中一個迴圈中將 Array.find 替換為 Map.get,我能夠將迭代總數從 12 次減少到 9 次。雖然減少 3 個迴圈看起來不顯著,但演算法的複雜度卻變得很高O(n m),函數執行時間減少了 96%,令人印象深刻!
在 Intel Core i7-10510U 上進行的測試中,使用陣列執行函數比使用 Map 和 Set 執行該函數花費的時間長 28 倍,使用包含 5,000 個項目的陣列:191.19 毫秒到 6.80 毫秒。
值得一提的是,雖然原始的陣列演算法具有 O(n * m) 複雜度,但執行時間隨著項目數量呈指數增長。在軟體開發場景中,考慮業務成長和執行程式碼的機器的限制至關重要。例如,如果陣列成長到 50,000 個項目,原始演算法的執行時間將為 13,585 毫秒,而使用 Set 和 Map 的最佳化演算法只需 135 毫秒。在這種情況下,原始演算法將慢 100 倍,優化後執行時間減少 99%。
考慮到 Set 和 Map 與 Array 相比在資訊檢索方面的速度優勢,當需要在 Array.filter 或 Array.find 等迭代中檢查此資訊時,迭代創建 Set 或 Map 的成本是合理的。
但是,由於一些缺點,例如缺乏順序排序、無法透過索引直接存取元素以及不儲存重複元素的限制,Set 的使用可能並不總是可行。
儘管有這些限制,但在許多情況下,用 Set 或 Map 取代陣列可以在效能和效率方面帶來顯著的優勢。
以上是我如何透過以下方式加速 Javascript 函數:的詳細內容。更多資訊請關注PHP中文網其他相關文章!