Dav*_*nes 7 reactjs next.js use-effect
我不明白为什么我的useEffect()React 函数无法访问我的组件的状态变量。当用户放弃在我们的应用程序中创建列表并导航到另一个页面时,我试图创建一个日志。我正在使用useEffect() return复制componentWillUnmount()生命周期方法的方法。你能帮我吗?
let[progress, setProgress] = React.useState(0)
... user starts building their listing, causing progress to increment ...
console.log(`progress outside useEffect: ${progress}`)
useEffect(() => {
return () => logAbandonListing()
}, [])
const logAbandonListing = () => {
console.log(`progress inside: ${progress}`)
if (progress > 0) {
addToLog(userId)
}
}
Run Code Online (Sandbox Code Playgroud)
代码将达到addToLog(),导致记录此行为。
这就是当用户在他们的列表中输入一些内容,导致progress增加,然后离开页面时发生的情况。
useEffect()方法完美运行,并触发该logAbandonListing()功能console.log()(上面useEffect)记录了大于 0 的progress状态console.log()用于日志0progress状态,禁用代码返回true的if语句,并达到addToLog()功能。我真的很感激一些帮助理解这里发生的事情。谢谢。
Pet*_*uzs 13
我认为这是一个典型的陈旧关闭问题。而且一开始很难理解。
对于空的依赖数组,useEffect 将只运行一次。它将从那一次运行访问状态。所以从这一刻起,它将有一个来自 logAbandonListing 函数的引用。此函数也将从这一刻开始访问状态。您可以通过多种方式解决问题。
其中之一是将状态变量添加到您的依赖项中。
useEffect(() => {
return () => logAbandonListing()
}, [progress])
Run Code Online (Sandbox Code Playgroud)
另一种解决方案是将状态值设置为 ref。并且 ref 的引用不会改变,因此您将始终看到最新鲜的值。
let[progress, setProgress] = React.useState(0);
const progressRef = React.createRef();
progressRef.current = progress;
...
const logAbandonListing = () => {
console.log(`progress inside: ${progressRef.current}`)
if (progressRef.current > 0) {
addToLog(userId)
}
}
Run Code Online (Sandbox Code Playgroud)
如果 userId 也在更改,那么您应该将其添加到依赖项或引用中。
小智 7
要在依赖项为空数组useEffect的返回函数中对状态的当前值执行某些操作,您可以使用. 这样您就可以避免过时的关闭问题并从 的函数更新状态。useEffects[]useReduceruseReducerdispatch
例子是:
import React, { useEffect, useReducer } from "react";
function reducer(state, action) {
switch (action.type) {
case "set":
return action.payload;
case "unMount":
console.log("This note has been closed: " + state); // This note has been closed: 201
break;
default:
throw new Error();
}
}
function NoteEditor({ initialNoteId }) {
const [noteId, dispatch] = useReducer(reducer, initialNoteId);
useEffect(function logBeforeUnMount() {
return () => dispatch({ type: "unMount" });
}, []);
return <div>{noteId}</div>;
}
export default NoteEditor;
Run Code Online (Sandbox Code Playgroud)
有关此答案的更多信息
| 归档时间: |
|
| 查看次数: |
5780 次 |
| 最近记录: |