React Hooks 的优势和使用场景

17 阅读2分钟
# React Hooks 的优势和使用场景

## 1. React Hooks 的核心优势

### 1.1 简化组件逻辑
Hooks 允许在不编写 class 的情况下使用 state 和其他 React 特性。通过 `useState` 可以轻松管理组件状态:

```jsx
function Counter() {
  const [count, setCount] = useState(0);
  return (
    <button onClick={() => setCount(count + 1)}>
      Clicked {count} times
    </button>
  );
}

1.2 逻辑复用能力

自定义 Hook 可以提取组件逻辑到可重用的函数中:

function useWindowWidth() {
  const [width, setWidth] = useState(window.innerWidth);
  
  useEffect(() => {
    const handleResize = () => setWidth(window.innerWidth);
    window.addEventListener('resize', handleResize);
    return () => window.removeEventListener('resize', handleResize);
  }, []);

  return width;
}

1.3 更细粒度的代码组织

相关逻辑可以集中在一起,而不是分散在不同的生命周期方法中:

function UserProfile({ userId }) {
  // 数据获取逻辑集中
  const [user, setUser] = useState(null);
  useEffect(() => {
    fetchUser(userId).then(setUser);
  }, [userId]);

  // 订阅逻辑集中
  useEffect(() => {
    const subscription = subscribeToUser(userId);
    return () => unsubscribe(subscription);
  }, [userId]);
}

2. 主要 Hooks 使用场景

2.1 useState - 状态管理

适用于:

  • 组件本地状态
  • 表单控制
  • 简单的 UI 状态切换
function Form() {
  const [name, setName] = useState('');
  return <input value={name} onChange={e => setName(e.target.value)} />;
}

2.2 useEffect - 副作用处理

适用于:

  • 数据获取
  • 订阅
  • 手动 DOM 操作
  • 其他副作用操作
useEffect(() => {
  document.title = `You clicked ${count} times`;
}, [count]); // 仅在 count 变化时更新

2.3 useContext - 跨组件共享

适用于:

  • 主题切换
  • 用户认证信息
  • 全局配置
const ThemeContext = createContext('light');

function App() {
  return (
    <ThemeContext.Provider value="dark">
      <Toolbar />
    </ThemeContext.Provider>
  );
}

function Toolbar() {
  const theme = useContext(ThemeContext);
  return <div style={{ background: theme === 'dark' ? '#333' : '#FFF' }} />;
}

2.4 useReducer - 复杂状态逻辑

适用于:

  • 复杂的状态逻辑
  • 多个子值相互依赖的状态
  • 全局状态管理
function reducer(state, action) {
  switch (action.type) {
    case 'increment':
      return {count: state.count + 1};
    case 'decrement':
      return {count: state.count - 1};
    default:
      throw new Error();
  }
}

function Counter() {
  const [state, dispatch] = useReducer(reducer, {count: 0});
  return (
    <>
      Count: {state.count}
      <button onClick={() => dispatch({type: 'increment'})}>+</button>
    </>
  );
}

3. 高级 Hooks 应用

3.1 useMemo - 性能优化

适用于计算开销大的值:

const memoizedValue = useMemo(() => computeExpensiveValue(a, b), [a, b]);

3.2 useCallback - 函数记忆

适用于防止不必要的子组件重渲染:

const memoizedCallback = useCallback(() => {
  doSomething(a, b);
}, [a, b]);

3.3 useRef - 持久化引用

适用于:

  • 访问 DOM 元素
  • 保存可变值而不触发重渲染
function TextInput() {
  const inputEl = useRef(null);
  const focusInput = () => inputEl.current.focus();
  
  return (
    <>
      <input ref={inputEl} type="text" />
      <button onClick={focusInput}>Focus</button>
    </>
  );
}

4. Hooks 最佳实践

  1. 只在顶层调用 Hooks
    • 不要在循环、条件或嵌套函数中调用

2