在 React 世界中,大多數開發人員在元件渲染方法中使用閉包時不會三思而後行,尤其是在映射列表時。
但是如果我告訴您有一個未充分利用但功能強大的替代方案,它可以幫助提高效能、可讀性,甚至更好地與工具集成,您會怎麼想?
讓我們來談談HTML data-* 屬性:前端開發人員很少使用但值得重新檢視的功能。
HTML 的data-*
屬性讓你在 DOM 元素中嵌入自訂資料。在純 HTML 中:
<div data-user-id="123" data-role="admin">John</div>
在React中,你可以按照相同的方式使用它們:
<div data-user-id={user.id} data-role={user.role}>
{user.name}
</div>
它們可以透過資料集物件在事件處理程序中存取:
e.currentTarget.dataset.userId;
假設您正在渲染一個專案清單:
{items.map((item) => (
<button key={item.id} onClick={() => handleClick(item.id)}>
{item.name}
</button>
))}
效果很好。它可讀性強,易於編寫。
但在幕後,您為每個渲染中的每個專案建立一個新函數:一個捕獲item.id
的閉包。
在許多應用中,這並沒有實際影響。然而…
雖然閉包是 JavaScript 和 React 的基本組成部分,但在.map()
中使用它們可能會有缺點:
如果您使用React.memo
、 React.useCallback
或虛擬化清單(例如react-window ),新的函數參考可能會導致不必要的重新渲染。由於每次都會重新建立函數,因此記憶化功能也無濟於事。
想像一下,你正在建立一個高度互動的列表,需要渲染數百個專案。最小化重新渲染變得至關重要,而內嵌閉包可以解決這個問題。
data-*
無需為每個專案建立閉包,而是使用data-*
將元資料直接附加到 DOM:
function handleClick(e) {
const id = e.currentTarget.dataset.id;
console.log("Clicked item:", id);
}
{items.map((item) => (
<button key={item.id} data-id={item.id} onClick={handleClick}>
{item.name}
</button>
))}
單函數引用→ 與React.memo
或React.useCallback
完美相容
改進了大型清單或重新渲染敏感元件的效能
因為閉包對於大多數應用程式來說都很簡單、直觀且性能足夠好。 data- data-*
感覺有點“老派”,在現代 React/Frontend 教程中很少提及。
但在表現或記憶很重要的情況下,這種方法可能是一個隱藏的寶石。
雖然data-*
屬性不是 React 開發人員工具箱中的常用工具,但它們在特定場景中提供了真正的優勢:
減少不必要的函數建立
提高記憶和渲染效能
實現更簡單、更清晰的事件處理
它們不能取代閉包,但當效能或架構需要時,它們是一個很好的替代品。
你曾經使用過類似的data-*
屬性嗎?還是你通常堅持使用閉包?我很想聽聽你的想法和經驗!
希望你覺得這篇文章有趣。在留言處留言告訴我你的想法👇
原文出處:https://dev.to/moruno21/99-of-frontend-devs-dont-use-this-1g44