很抱歉,标题令人困惑,但下面是发生的情况:
在MyComponent
中,我正在使用useState
React钩子设置count
状态。一旦组件挂载(即没有依赖项的useffect
),我将实例化两个MyClass
对象,其中第一个参数作为一个回调函数来递增状态,第二个参数是调用回调函数的超时时间。
MyClass
的第一个实例在1000毫秒内调用回调,并为count
设置新值,该值一旦更新,将记录在第二个useffect
中。
但是,当
MyClass
的第二个实例调用回调(在timeOut
3000毫秒之后),并尝试增加count
值时,它使用了MyClass
实例化时的count
状态(该状态为0),因此它将count
增加到1(想要的行为是增加到2,因为MyClass
的第一个实例已经从0增加到1)
这与
setState
的异步行为无关,因为很明显,对count
的第一次更新发生在第二个实例再次尝试更新之前(第二个useffect
在更新count
状态时被调用,您可以从控制台日志消息中看到,在第二个MyClass
实例调用回调之前,会调用第二个useffect
)。
JSIDLE链接:https://jsfiddle.net/hfv24dpL/
总之,我认为问题在于回调函数中的
count
状态是回调函数传递给MyClass
构造函数时count
状态的副本。
这个例子的一个解决方案可以是在更新
Count
状态时(在第二个use效应
中)实例化MyClass
的第二个实例,但这不是我要找的解决方案。
另一种解决方案是使用
setCount(prevCount=
我希望能够在组件装载时(在first
useEffect
中)实例化类,并使回调引用最新版本的count
。
是否有解决方案^或者没有办法绕过此javascript和React实现?感谢您阅读所有这些,我知道它很长:)
import React, { useState, useEffect } from 'react';
class MyClass{
constructor(callback, timeOut){
// call callback in timeOut milliseconds
this.timeOutId = setTimeout(() => {
callback();
}, timeOut)
}
clearTimeOut(){
clearTimeout(this.timeOutId);
}
}
function MyComponent(){
var [count, setCount] = useState(0);
// component did mount
useEffect(() => {
let myClass1 = new MyClass(funcToCallback, 1000);
let myClass2 = new MyClass(funcToCallback, 3000);
// when component unmounts, clear the timeouts of MyClass instances
return () => {
myClass1.clearTimeOut();
myClass2.clearTimeOut();
}
}, []);
// counter state updated
useEffect(() => {
console.log("COUNT UPDATED TO: ", count);
}, [count])
// get counter and increment it by 1
function funcToCallback(){
console.log("CALLBACK CALLED");
let newCount = count + 1;
incCount(newCount);
}
function incCount(newCount){
console.log("NEW COUNT: ", newCount);
setCount(newCount);
}
return (
<div>
COUNT: { count }
</div>
)
}
当count
为0时,使用的funcToCallback
是组件初始装载中的一个。使用const
声明的变量不会更改,useffect
回调只调用一次,funcToCallback
关闭的count
永远保持为0。
最简单的修复方法是改用setter的函数版本,它会将先前的状态作为参数提供给您,然后您可以增加它。改变
function incCount(newCount){
console.log("NEW COUNT: ", newCount);
setCount(newCount);
}
到
function incCount(){
setCount((lastCount) => {
console.log("NEW COUNT: ", (lastCount + 1));
return lastCount + 1;
});
}
但是控制台显示一个错误: 未捕获的 DOMException:无法在 “History” 上执行 'pushState':无法克隆 Symbol(react.element)。 这是什么意思?对此我能做些什么?
问题内容: 我的工厂如下 这是Foo的定义: 好。我不确定如何使用Guice将此参数传递给Foo构造函数? 有任何想法吗? 问题答案: 所有“ Guice构造函数参数”答案在某种程度上似乎都不完整。这是一个完整的解决方案,包括用法: //在实现类上注释构造函数和辅助参数 //使用仅接受辅助参数的create()方法创建工厂接口。 // FooFactory接口没有显式的实现类(Guice Magi
我的Navbar组件有2个子组件。每个组件都有自己的状态。在其组成部分内工作正常的国家。如何更新这两个状态从假到真的同时,当两个功能onclick将被执行? 主组件导航栏 列表菜单组件 汉堡包成分
当我们在ReactJS状态上存储函数时,我在这里遇到了一些非常奇怪的事情。 我用钩子创建了一个react状态,其中包含: 数字变量 回调函数 由于钩子本身在setState期间没有回调,所以我使用此方法在状态更改后的useEffect期间切换回调。 我在setState期间传递的回调是打印state.number和secondNumber值的值。设置状态完成后,state.number的值应为4,
我试图做一个登录表单,它需要我迁移我的soloreac应用程序在反应redux应用程序。我面临许多错误,并坚持与。我是这方面的新手,任何帮助都会得到重视。 指数js文件 应用程序。js文件: 我得到这个错误。我不明白是什么文件或代码导致了这个错误。 类型错误:存储。getState不是新提供程序节点的函数\u modules/react redux/es/components/Provider。j
这两个是等价的吗?如果不是,哪一个是最好的,为什么?