useEffect React钩子将在每次更改时运行传入函数。可以对其进行优化,使其仅在所需属性更改时调用。

如果我想从componentDidMount调用初始化函数,而不是在更改时再次调用它,该怎么办?假设我想加载一个实体,但加载函数不需要来自组件的任何数据。我们如何使用useEffect钩子来实现这个?

class MyComponent extends React.PureComponent {
    componentDidMount() {
        loadDataOnlyOnce();
    }
    render() { ... }
}

如果使用钩子,可能是这样的:

function MyComponent() {
    useEffect(() => {
        loadDataOnlyOnce(); // this will fire on every change :(
    }, [...???]);
    return (...);
}

当前回答

如果您只想在初始呈现后运行给useEffect的函数,可以给它一个空数组作为第二个参数。

function MyComponent() {
  useEffect(() => {
    loadDataOnlyOnce();
  }, []);

  return <div> {/* ... */} </div>;
}

其他回答

博士TL;

useEffect(yourCallback,[]) -只在第一次渲染后触发回调。

详细解释

默认情况下,useEffect在每次呈现组件后运行(因此会产生效果)。

当在你的组件中放置useEffect时,你告诉React你想要运行回调作为一个效果。React将在渲染和执行DOM更新后运行效果。

如果你只传递一个回调-回调将在每次渲染后运行。

如果传递第二个参数(数组),React将在第一次渲染后和每次数组中的一个元素被更改时运行回调。例如,当放置useEffect(() => console.log('hello'), [someVar, someOtherVar])时,回调将在第一次渲染之后和someVar或someOtherVar中的一个被更改的任何渲染之后运行。

通过将第二个参数传递给一个空数组,React将在每次渲染数组后进行比较,并且不会看到任何更改,因此只在第一次渲染后调用回调。

将一个空数组作为第二个参数传递给useEffect。这有效地告诉React,引用文档:

这告诉React,你的效果不依赖于道具或状态的任何值,所以它永远不需要重新运行。

这是一个片段,你可以运行,以显示它的工作:

function App() { const [user, setUser] = React.useState(null); React.useEffect(() => { fetch('https://randomuser.me/api/') .then(results => results.json()) .then(data => { setUser(data.results[0]); }); }, []); // Pass empty array to only run once on mount. return <div> {user ? user.name.first : 'Loading...'} </div>; } ReactDOM.render(<App/>, document.getElementById('app')); <script src="https://unpkg.com/react@16.7.0-alpha.0/umd/react.development.js"></script> <script src="https://unpkg.com/react-dom@16.7.0-alpha.0/umd/react-dom.development.js"></script> <div id="app"></div>

窗口。即使用户按下返回按钮导航到页面,Onpageshow也能工作,这与传递一个空数组作为use-effect钩子的第二个参数不同,后者在通过返回按钮返回页面时不会触发(因此不是在每一种形式的初始页面加载上)。

 useEffect(() => {    
     window.onpageshow = async function() {
      setSomeState(false)
      let results = await AsyncFunction() 
       console.log(results, 'Fires on on first load, 
        refresh, or coming to the page via the back button')
    };
 };

如果您只想在初始呈现后运行给useEffect的函数,可以给它一个空数组作为第二个参数。

function MyComponent() {
  useEffect(() => {
    loadDataOnlyOnce();
  }, []);

  return <div> {/* ... */} </div>;
}

将依赖项数组保留为空。希望这能帮助你更好地理解。

   useEffect(() => {
      doSomething()
    }, []) 

空依赖数组只在挂载时运行一次

useEffect(() => {
  doSomething(value)
}, [value])  

将值作为依赖项传递。如果依赖关系自上次以来发生了变化,该效果将再次运行。

useEffect(() => {
  doSomething(value)
})  

没有依赖。这个在每次渲染后都会被调用。