在 react 中实现防抖和节流,核心思路是将这些逻辑封装为自定义 hook,并在组件的 useeffect 依赖数组中管理定时器。通过这种方式,可以在组件卸载时自动清理资源,避免内存泄漏,同时确保状态更新与渲染周期同步。

如何编写一个通用的防抖 Hook
编写防抖 Hook 的关键在于使用 useRef 来存储最新的回调函数,从而解决闭包陷阱问题。这样即使组件重新渲染,定时器执行时调用的也是最新版本的函数逻辑。

import { useState, useEffect, useRef } from 'react';
function useDebounce(callback, delay) {
const timeoutRef = useRef(null);
const callbackRef = useRef(callback);
// 始终保存最新的回调函数
useEffect(() => {
callbackRef.current = callback;
}, [callback]);
const debouncedFn = (...args) => {
if (timeoutRef.current) {
clearTimeout(timeoutRef.current);
}
timeoutRef.current = setTimeout(() => {
callbackRef.current(...args);
}, delay);
};
// 组件卸载时清理定时器
useEffect(() => {
return () => {
if (timeoutRef.current) {
clearTimeout(timeoutRef.current);
}
};
}, []);
return debouncedFn;
}
如何编写一个通用的节流 Hook
节流 Hook 的实现通常基于时间戳或标志位。这里采用时间戳方案,记录上次执行的时间,只有当距离上次执行超过指定间隔时才触发回调。同样需要处理依赖更新和清理逻辑。
构建 Shopify 嵌入式应用(Embedded App)的开发技能:基于 @shopify/shopify-app-react-router + React Router v7 + Admin API 2026-04。覆盖 shopifyApp 配置、authenticate.admin 的 GraphQL/REST 调用、Webhook 校验、Session 存储、订阅计费、App Bridge 导航、部署,并新增:适用场景判断、安全最佳实践、错误处理与容错、最佳实践、常见问题 FAQ、高级场景。G

import { useState, useEffect, useRef } from 'react';
function useThrottle(callback, limit) {
const lastTimeRef = useRef(0);
const timeoutRef = useRef(null);
const callbackRef = useRef(callback);
useEffect(() => {
callbackRef.current = callback;
}, [callback]);
const throttledFn = (...args) => {
const now = Date.now();
const remaining = limit - (now - lastTimeRef.current);
if (remaining {
lastTimeRef.current = Date.now();
timeoutRef.current = null;
callbackRef.current(...args);
}, remaining);
}
};
useEffect(() => {
return () => {
if (timeoutRef.current) {
clearTimeout(timeoutRef.current);
}
};
}, []);
return throttledFn;
}
在搜索输入框中结合两者使用的具体场景
在实际开发中,搜索框往往需要防抖来减少请求频率,而滚动加载可能需要节流来控制事件触发次数。以下是一个完整的示例,展示如何在同一个组件中同时使用这两个 Hook 来处理不同的交互。
Java免费学习笔记:立即使用
解锁 Java 大师之旅:从入门到精通的终极指南










