reactjs - 简单的计数器不会停止使用 useEffect 钩子在功能组件内部递增
问题描述
我试图在功能组件的 useEffect Hook 中使用 rxjs。
我相信 useEffect 可以像 componentDidMount 和 componentDidUpdate 一样使用。
const Counter = () => {
const [state, setState] = useState({counter: 0});
useEffect(() => {
subscriber.subscribe((value) => {
let { counter } = state;
counter += value;
setState({ counter });
});
});
return (
<div>
<span>Counter: {state.counter}</span>
<Crementer />
</div>
);
订阅者是一个简单的 rxjs 主题
const subscriber = new BehaviorSubject(0);
还有一个组件可以增加/减少计数器
const Crementer = () => {
return(
<>
<button onClick={() => subscriber.next(1)}>+</button>
<button onClick={() => subscriber.next(-1)}>-</button>
</>
)
};
(我也试过 counterService.send(1) )
问题是只要我单击 + 或 - 计数器就会连续递增或递减。
您可以在此处查看行为:https ://stackblitz.com/edit/react-9auz4d
也许是因为 useEffect 也在更新时运行?它可能会在带有 componentDidMount() 的类组件中工作?
解决方案
每次更新都会调用挂钩:https ://reactjs.org/docs/hooks-effect.html#explanation-why-effects-run-on-each-update
因此,您可以存储订阅返回的表单subscribe
调用,然后将其保存在另一个useState
. 在每次效果调用时,您只需检查它是否已设置。顺便说一句,你还应该从这个效果中返回一个拆卸函数,这样你也需要订阅。
或者最终您可以使用第二个参数useEffect
只运行一次(如何使用 React useEffect 调用加载函数仅一次):
useEffect(() => {
const subscription = observable.subscribe((value) => {
let { counter } = state;
counter += value;
setState({ counter });
});
return () => subscription.unsubscribe();
}, []);
推荐阅读
- r - rstan 将数据存储为矩阵或 data.frame 更快地拟合模型吗?
- java - 无法将文本从外部片段放入 textview?
- vba - SendUsingAccount SendAs 权限但未在索引中找到
- python - Performing a row sum and column sum on a list of lists in python
- powershell - 为什么 Send-MailMessage 无法通过端口 587 使用 STARTTLS 发送
- gulp - 如何修复 Gulpfile 中的浏览器同步和实时重新加载?
- regex - 在python中用“\n”替换所有类型的换行符
- c# - c# / .net 中是否有相当于 MySQL 的 show columns 语句?
- amazon-web-services - 无法获得正确的 URL 重定向到我的网站
- python - 根据索引在同一位置绘制两个数据集