我试图用数组更新状态。但是我需要保留数组中现有的信息,并将更多的信息推入其中。
这是我的状态:
const [filteredProducts, setFilteredProducts] = useState([]);
这是我为onClick事件监听器调用的函数
const filteredByCategory = (event, category, products) => {
const element = document.getElementById(event.target.id);
if (element.checked) {
const productsToAdd = products.filter(
(product) => product.category === category
);
setFilteredProducts((currentFilteredProducts) => [
...currentFilteredProducts,
...productsToAdd,
]);
dispatch({
type: "PRODUCTS_FILTERED",
payload: filteredProducts,
});
} else {
let removedCheckedProducts = filteredProducts.filter((product) => {
return product.category !== category;
});
setFilteredProducts(removedCheckedProducts);
if (removedCheckedProducts.length >= 1) {
dispatch({
type: "PRODUCTS_FILTERED",
payload: removedCheckedProducts,
});
} else {
dispatch({
type: "PRODUCTS_FILTERED",
payload: allProducts,
});
}
}
};
我的假设是您期望filteredProducts
状态值反映您在setFilteredProducts
之后的更改:
setFilteredProducts((currentFilteredProducts) => [
...currentFilteredProducts,
...productsToAdd,
]);
dispatch({
type: "PRODUCTS_FILTERED",
payload: filteredProducts,
});
不幸的是,状态更新不是这样工作的。set*
函数只是为下一次渲染排队更新,但不会立即更新状态。
您可以维护一个本地变量,以将更新传递到本地状态和Redux存储:
const updatedProducts = [
...filteredProducts,
...productsToAdd,
];
setFilteredProducts(updatedProducts);
dispatch({
type: "PRODUCTS_FILTERED",
payload: updatedProducts,
});
digitalbreed在他的答案中正确地识别了竞争状况。在单击addProduct
按钮