gpt4 book ai didi

javascript - 无法分配给对象 'property' 的只读属性 '#'
转载 作者:行者123 更新时间:2023-12-02 16:18:30 26 4
gpt4 key购买 nike

我有这个问题。

带接口(interface):

export interface IDevice {
id: string,
selected: boolean
}

通过以下方式创建实例:

let newDevice: IDevice = {
id: uuid4(),
selected: false,
} as IDevice;

它以反冲状态添加到数组中,并在 React 中用在函数中,其中数组已通过 useRecoilState() 检索。 const [leftList, setLeftList] = React.useState<IDevice[]>([]);

现在它被用于选择列表控件上的设备的处理程序中,这里发生错误:

...
leftList.map((item: IDevice) => {
if (item.id === event.dataItem.id) {
item.selected = !item.selected;
}
return item;
})
...

我收到错误:无法分配给对象“#”的只读属性“selected”

即使先通过 [...leftList] 克隆数组也无济于事。

我迷路了:-) 希望有人能阐明这一点?

最佳答案

不应直接修改状态,这是您当前在 .map() 方法中通过更新对象所做的事情。 TS 试图通过将您的对象设为只读来告诉您不要这样做。

相反,您可以使用 item 中的所有属性创建一个新对象(使用 spread syntax ... 完成),以及一个新的覆盖属性 selected,这将如果 id 与事件的数据项 id 匹配,则使用该项目当前选定项目的否定版本,否则它将保留原始选定值:

leftList.map((item: IDevice) => ({
...item,
selected: item.id === event.dataItem.id ? !item.selected : item.selected
}))

使用扩展语法 ([...leftList]) 克隆数组只会进行浅拷贝,不会对其中的对象进行深拷贝,因此,修改 .map() 中的对象引用仍然是修改原始状态。

或者,不是传播 item 对象并每次都创建一个新对象(这会稍微影响性能,正如 @3limin4t0r 所指出的那样),您可以只返回一个新创建的对象当你想修改 selected 属性时:

leftList.map((item: IDevice) => {     
if (item.id !== event.dataItem.id) return item;
return {...item, selected: !item.selected};
});

关于javascript - 无法分配给对象 'property' 的只读属性 '#<Object>',我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/66116609/

26 4 0