React Hooks 初步尝试

9 篇文章 0 订阅

HOOK-API

1. 基础 Hook

1. useState

// 返回一个 state,以及更新 state 的函数。
const [state, setState] = useState(initialState);
  • 惰性初始 state
/* 如果初始 state 需要通过复杂计算获得,则可以传入一个函数,
在函数中计算并返回初始的 state,此函数只在初始渲染时被调用:*/
const [state, setState] = useState(() => {
  const initialState = someExpensiveComputation(props);
  return initialState;
});

 

2. useEffect

// 接收一个包含命令式、且可能有副作用代码的函数。
// 如: 改变 DOM、添加订阅、设置定时器、记录日志以及执行其他包含副作用的操作
// 虽然 useEffect 会在浏览器绘制后延迟执行,但会保证在任何新的渲染前执行
// 用户可见的 DOM 变更,可使用 useLayoutEffect
useEffect(didUpdate);

// 代码示例
useEffect(
  () => {
    // 这里写 componentDidMount、componentDidUpdate 的操作
    const subscription = props.source.subscribe();
    return () => {
      // 此处类似 componentWillUnMonut
      subscription.unsubscribe();
    };
  },
  // 这里是限制当 props.source改变时,才执行方法体的方法
  [props.source],
);

3. useContext

// 接收一个 context 对象(React.createContext 的返回值)并返回该 context 的当前值。
/* useContext(MyContext) 只是让你能够读取 context 的值以及订阅 context 的变化。
你仍然需要在上层组件树中使用 <MyContext.Provider> 来为下层组件提供 context。*/
const value = useContext(MyContext);

2. 额外的 Hook

1. useReducer

/* 它接收一个形如 (state, action) => newState 的 reducer,
并返回当前的 state 以及与其配套的 dispatch 方法。*/
const [state, dispatch] = useReducer(reducer, initialArg, init);
  • 惰性初始化
// 将 init 函数作为 useReducer 的第三个参数传入,这样初始 state 将被设置为 init(initialArg)。
function init(initialCount) {
  return {count: initialCount};
}
function reducer(state, action) {
  switch (action.type) {
    case 'increment':
      return {count: state.count + 1};
    case 'decrement':
      return {count: state.count - 1};
    case 'reset':
      return init(action.payload);
    default:
      throw new Error();
  }
}
function Counter({initialCount}) {
  const [state, dispatch] = useReducer(reducer, initialCount, init);
  return (
  );
}

2. useCallback

3. useMemo

// 把“创建”函数和依赖项数组作为参数传入 useMemo,它仅会在某个依赖项改变时才重新计算 memoized 值。
// 这种优化有助于避免在每次渲染时都进行高开销的计算。
// (先编写在没有 useMemo 的情况下也可以执行的代码 —— 之后再在你的代码中添加 useMemo,以达到优化性能的目的。)
const memoizedValue = useMemo(() => computeExpensiveValue(a, b), [a, b]);

4. useRef

/* useRef 返回一个可变的 ref 对象,其 .current 属性被初始化为传入的参数(initialValue)。
返回的 ref 对象在组件的整个生命周期内保持不变。*/
const refContainer = useRef(initialValue);

5. useImperativeHandle

/* useImperativeHandle 可以让你在使用 ref 时自定义暴露给父组件的实例值。
在大多数情况下,应当避免使用 ref 这样的命令式代码。
useImperativeHandle 应当与 forwardRef 一起使用:*/
useImperativeHandle(ref, createHandle, [deps])
  • 一个例子
function FancyInput(props, ref) {
  const inputRef = useRef();
  useImperativeHandle(ref, () => ({
    focus: () => {
      inputRef.current.focus();
    }
  }));
  return <input ref={inputRef} ... />;
}
FancyInput = forwardRef(FancyInput);

6. useLayoutEffect

    • 可以使用它来读取 DOM 布局并同步触发重渲染。
    • 尽可能使用标准的 useEffect 以避免阻塞视觉更新。

7. useDebugValue

// useDebugValue 可用于在 React 开发者工具中显示自定义 hook 的标签。
useDebugValue(value)
  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值