是的,这个问题似乎与这个问题重复:
每个组件应该有一个 useDispatch 吗?
但它并不重复。我提供不同的方法:
假设我有 3 个子组件,它们都使用 Redux Toolkit 的调度函数。
通常的方式是这样的:
const ChildA = () => {
const dispatch = useAppDispatch();
const incr = useCallback(() => {
dispatch(increment());
}, [dispatch]);
return <button onClick={incr}>ChildA</button>;
};
const ChildB = () => {
const dispatch = useAppDispatch();
const incr = useCallback(() => {
dispatch(increment());
}, [dispatch]);
return <button onClick={incr}>ChildB</button>;
};
const ChildC = () => {
const dispatch = useAppDispatch();
const incr = useCallback(() => {
dispatch(increment());
}, [dispatch]);
return <button onClick={incr}>ChildC</button>;
};
export const MyApp = () => {
const dispatch = useAppDispatch();
const count = useAppSelector((state) => state.counter.value);
const incr = useCallback(() => {
dispatch(increment());
}, [dispatch]);
return (
<div>
<button onClick={incr}>MyApp</button>
<ChildA />
<ChildB />
<ChildC />
<div>{count}</div>
</div>
);
};
但是如果我这样做呢?请参阅:
export const glo: {
dispatch: ReturnType<typeof useAppDispatch>;
} = {
// @ts-ignore
dispatch: null
};
const ChildA = () => {
const incr = useCallback(() => {
glo.dispatch(increment());
}, []);
return <button onClick={incr}>ChildA</button>;
};
const ChildB = () => {
const incr = useCallback(() => {
glo.dispatch(increment());
}, []);
return <button onClick={incr}>ChildB</button>;
};
const ChildC = () => {
const incr = useCallback(() => {
glo.dispatch(increment());
}, []);
return <button onClick={incr}>ChildC</button>;
};
export const MyApp = () => {
const dispatch = useAppDispatch();
glo.dispatch = dispatch;
if (!glo.dispatch) {
throw new Error("dispatch is falsy");
}
const count = useAppSelector((state) => state.counter.value);
const incr = useCallback(() => {
glo.dispatch(increment());
}, []);
return (
<div>
<button onClick={incr}>MyApp</button>
<ChildA />
<ChildB />
<ChildC />
<div>{count}</div>
</div>
);
};
经我测试,它也运行良好。请告诉我,为什么我应该按照通常的方式做?现在新代码(基于 glo 的代码)更大,但那是因为我们只有 3 个子组件。当我们有 30 多个子组件时,基于 glo 的代码将会小得多,也更容易理解。
这里是差异:
https://i.ibb.co/tKWv2Qc/image.png
这是 CodeSandbox 链接:
https://codesandbox.io/s/clever-monad-c99q3k?file=/src/features/index.tsx
Copyright 2014-2025 https://www.php.cn/ All Rights Reserved | php.cn | 湘ICP备2023035733号
例如,该调度函数将在您的测试中发生变化。
如果没有测试,在某些环境中这样做本身并不是“错误”,但也不是一个大胜利。
如果你的应用程序中有一行
const dispatch = useAppDispatch();,那么很有可能,当 js 包被 gzip 传输时(现在这很正常),它会 gzip 到 3 或 4无论如何字节。如果您确实想删除此处的代码,请删除
useCallback,因为将回调直接传递到 html 时完全没有必要。