UseState stepping on the pit in React hooks-=-asynchronous problem

As the most common hook, useState always has various pitfalls in use, the most obvious one is the problem of asynchronous useStateupdate .

For example, we useStatestore , but when we change the data later, we get the last data every time, which cannot be updated in real time.

Or we use setState inside the function, and then print the state immediately, and the printed result is still the value of the first state. For example, the following code example.

  const [data, setData] = useState('111');

  const handleTest = () => {
    
    
    console.log(data) // 111
    setName('222')
    console.log(name) // 111
  }

reason:

The method of updating the object returned by useState is asynchronous, and the new value can only be obtained after the next redraw. Do not try to obtain the state immediately after changing the state.

1. Two ways to use useState

We know that [] in useState is a deconstruction operation, the first is the set value, and the second is the method used to change the state.

1. Pass in new values ​​directly

const [data, setData] = useState(1)
setData(data + 1)

2. Pass in the callback function setState(callback)

const [data, setData] = useState(0)
setData((prev) => prev + 1); // prev 是data 改变之前的值,return 返回的值会作为新状态覆盖data

In general, we can use the first method, but in some special cases, the value obtained by the first method is not the latest setting.

2. Solutions

2.1 Using useRef

Idea: first use useRefto store data, and then use useEffectto monitor data changes and update them.

import React, {
    
     useState, useEffect, useRef } from 'react';

const Index = () => {
    
    
	const [info, setInfo] = useState()
	const infoRef = useRef()
	useEffect(() => {
    
    
		infoRef.current = info
	}, [info])
}

Where you need to use info data later, you only need infoRef.currentto to get the latest info data content.

2.2 Change data using callback function

const [data, setData] = useState({
    
    a: 1})
setData((prev) => {
    
    
	return {
    
    a: prev.a + 1}
})

Guess you like

Origin blog.csdn.net/qq_41131745/article/details/127704928
Recommended