前端面试题 - 26. React 中常用的 Hook 包括以下几个?

108 阅读2分钟

useState

用于在函数组件中添加状态管理功能,返回一个状态和一个更新状态的函数。

import React, { useState } from 'react';
function Example() {
  const [count, setCount] = useState(0);
  return (
    <div>
      <p>You clicked {count} times</p>
      <button onClick={() => setCount(count + 1)}>
        Click me
      </button>
    </div>
  );
}

useEffect

用于在函数组件中添加副作用操作,可以在组件渲染完成后执行一些操作,也可以在组件卸载前执行一些清理操作。

import React, { useState, useEffect } from 'react';
function Example() {
  const [count, setCount] = useState(0);
  useEffect(() => {
    document.title = `You clicked ${count} times`;
  }, [count]);
  return (
    <div>
      <p>You clicked {count} times</p>
      <button onClick={() => setCount(count + 1)}>
        Click me
      </button>
    </div>
  );
}

useContext

用于在函数组件中使用上下文(Context)对象,可以在组件树中任意层级传递数据。

import React, { useContext } from 'react';
const UserContext = React.createContext({});
function UserInfo() {
  const user = useContext(UserContext);
  return (
    <div>
      <p>User Name: {user.name}</p>
      <p>User Age: {user.age}</p>
    </div>
  );
}
function Example() {
  const user = { name: "Tom", age: 18 };
  return (
    <UserContext.Provider value={user}>
      <UserInfo />
    </UserContext.Provider>
  );
}

useReducer

类似于 Redux 中的 reducer,用于管理组件的状态,可以处理复杂的状态逻辑。

import React, { useReducer } from 'react';
const initialState = { count: 0 };
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, initialState);
  return (
    <div>
      <p>Count: {state.count}</p>
      <button onClick={() => dispatch({ type: 'increment' })}>+</button>
      <button onClick={() => dispatch({ type: 'decrement' })}>-</button>
    </div>
  );
}

useCallback

用于优化函数组件的性能,避免因为函数引用变化而导致子组件重复渲染。

import React, { useState, useCallback } from 'react';
function Example() {
  const [count, setCount] = useState(0);
  const increment = useCallback(() => {
    setCount(count + 1);
  }, [count]);
  return (
    <div>
      <p>You clicked {count} times</p>
      <button onClick={increment}>
        Click me
      </button>
    </div>
  );
}

useMemo

也用于优化函数组件的性能,避免因为计算开销大而导致组件重复渲染。

import React, { useMemo } from 'react';
function Example() {
  const [a, b] = [10, 20];
  const result = useMemo(() => a + b, [a, b]);
  return (
    <div>
      <p>Result: {result}</p>
    </div>
  );
}

useRef

用于在函数组件中保存可变的引用,可以保存组件之间共享的状态。

import React, { useRef } from 'react';
function Example() {
  const inputRef = useRef(null);
  const focusInput = () => {
    inputRef.current.focus();
  };
  return (
    <div>
      <input ref={inputRef} type="text" />
      <button onClick={focusInput}>Focus Input</button>
    </div>
  );
}

useImperativeHandle

用于在父组件中访问子组件的方法和状态,可以自定义暴露给父组件的接口。

import React, { forwardRef, useImperativeHandle } from 'react';
const FancyInput = forwardRef((props, ref) => {
  const inputRef = useRef(null);
  useImperativeHandle(ref, () => ({
    focus: () => {
      inputRef.current.focus();
    }
  }));
  return <input ref={inputRef} type="text" />;
});
function Example() {
  const inputRef = useRef(null);
  const focusInput = () => {
    inputRef.current.focus();
  };
  return (
    <div>
      <FancyInput ref={inputRef} />
      <button onClick={focusInput}>Focus Input</button>
    </div>
  );
}

useLayoutEffect

类似于 useEffect,但是会在 DOM 更新之前执行,可以用于获取 DOM 元素的尺寸和位置信息。

import React, { useLayoutEffect, useRef } from 'react';
function MeasureElement() {
  const ref = useRef(null);
  const [width, setWidth] = useState(0);
  useLayoutEffect(() => {
    setWidth(ref.current.offsetWidth);
  }, []);
  return (
    <div>
      <p ref={ref}>Measure my width</p>
      <p>My width is {width}px</p>
    </div>
  );
}

useDebugValue

用于在 React 开发者工具中显示自定义的 Hook 状态信息,方便调试。 以上是 React 中常用的 Hook,可以根据具体的业务场景选择合适的 Hook,提高组件的开发效率和性能。

import { useDebugValue, useState } from 'react';
function useStep(initialValue) {
  const [step, setStep] = useState(initialValue);
  useDebugValue(step);
  return setStep;
}
function Example() {
  const setStep = useStep(0);
  return (
    <div>
      <p>Step: {setStep}</p>
      <button onClick={() => setStep(step + 1)}>Next Step</button>
    </div>
  );
}