我的状态对象是一个Map
const [voucherSet, setVoucherSet] = useState(initialVoucherSet);
initialVoucherSet是我在无状态组件函数的开头创建的地图。
const initialVoucherSet = new Map();
activeVoucher.voucherDenominations.forEach(voucherDemonination=> {
initialVoucherSet.set(voucherDemonination, 0);
});
const [voucherSet, setVoucherSet] = useState(initialVoucherSet);
activeVoucher.voucherDenominations
一个数字数组。
我有一个输入会在onChange上触发一个函数。
const handleChange = (e)=>{
const voucherDemonination = parseInt(e.target.id);
const voucherQuantity = parseInt(e.target.value);
if (voucherQuantity >= 0) { setVoucherSet(voucherSet.set(voucherDemonination, voucherQuantity)); }
}
状态对象voucherSet正在更新,但我的输入值未重新呈现。
下面是输入元素:
<CounterInput type='number' id={voucherDemonination} onChange={handleChange} value={voucherSet.get(voucherDemonination)} />
我已经尝试过的内容 我认为这可能是因为我没有为voucherSet状态变量设置其他对象。所以我尝试了一些小技巧...
const handleChange = (e)=>{
const voucherDemonination = parseInt(e.target.id);
const voucherQuantity = parseInt(e.target.value);
if (voucherQuantity >= 0) {
const tempVoucherSet = voucherSet;
tempVoucherSet.set(voucherDemonination, voucherQuantity);
setVoucherSet(tempVoucherSet);
}
}
但是它仍然没有用。
我在哪里错了? 提前非常感谢! :)
答案 0 :(得分:1)
我过去有同样的问题。这样设置状态:
setVoucherSet(new Map(voucherSet.set(voucherDemonination, voucherQuantity)));
这将导致重新渲染。
答案 1 :(得分:1)
所以发生的事情是Map本身并没有发生变化(例如,每次更新Map时,您在内存中仍然引用了相同的精确Map),因此反应不会重新呈现。
这与整个“不变”事物发生反应。无论何时发生状态更改,都应创建一个新的对象或数组,以响应并轻松检测到某些更改并因此重新呈现。这样一来,您就不必在对象/数组中的每个键上进行迭代,以查看是否有任何更改(这会降低性能)。
在更新地图的代码中尝试以下操作:
tempVoucherSet.set(voucherDemonination, voucherQuantity);
setVoucherSet(new Map(tempVoucherSet)); // -> notice the new Map()
这类似于您可能在其他任何代码中看到的反应和状态更改,每次添加新属性/项目时都会创建新对象/数组:
setState({ ...oldState, newProperty: 'newValue' })
setState([ ...oldArray, newItem ]);