反应钩子:useState,嵌套在 for 循环中的更新器函数不更新状态

Posted

技术标签:

【中文标题】反应钩子:useState,嵌套在 for 循环中的更新器函数不更新状态【英文标题】:React hooks: useState, Updater function nested in for loop not updating state 【发布时间】:2021-06-21 17:13:31 【问题描述】:

我有一个 useEffect 钩子,我在其中通过换行符从状态中拆分字符串以创建数组,

该数组正在被循环,我想要将一个对象添加到我的状态/钩子(messageContainer)中,如果它不存在,则使用 id 和消息属性,例如 id: i, message: messageRow[i],或者如果它不存在则更新它它存在例如return ...messageObj, message: messageRow[i]

const [messages, setMessages] = useState('');

const [messagesContainer, setMessagesContainer] = useState([])

useEffect(() => 
var messageRow = messages.split('\n');

for (let i = 0; i < messageRow.length; i++) 
    setMessagesContainer(previousState => (
        [...previousState,
            ...previousState.map((messageObj, index, arr) => 
                if (messageObj.id === i) 
                    return 
                        ...messageObj,
                        message: messageRow[i]
                    
                 else 
                    return 
                        id: i,
                        message: messageRow[i]
                    
                
            )
        ]
    ))

, [messages])

messagesContainer 是空的吗?

如果数组有一个具有该属性的对象,我该如何更新它,或者如果它还不存在,我该如何添加它?

提前谢谢你!

更新:

正如下面提到的 Bart,我应该初始化 messageContainer

所以我做到了:

const [messagesContainer, setMessagesContainer] = useState([id: 0, messages: null])

但现在它只是附加到数组而不更新同一个对象:

【问题讨论】:

messagesContainer is coming back empty。什么时候? useEffect中的代码会传播previousState,映射其内容后再次传播previousState。但是previousState 在你开始时是空的,所以你永远不会添加任何东西。 太棒了!否则我该怎么办?或者怎么笑。 【参考方案1】:

在 useEffect 中尝试以下代码。它会起作用的。

useEffect(() => 
var messageRow = messages.split("\n");
let allMessages = [...messagesContainer]
for (let i = 0; i < messageRow.length; i++) 
  let match = allMessages.filter(item=>item.id===i);
  if(match?.length)
    match[0].messages=messageRow[i];
  
  else
    allMessages.push(id:i,messages:messageRow[i])
  

console.log(allMessages);
setMessagesContainer(allMessages);
, [messages]);

【讨论】:

以上是关于反应钩子:useState,嵌套在 for 循环中的更新器函数不更新状态的主要内容,如果未能解决你的问题,请参考以下文章

在 useState 钩子中反应设置状态

React useState钩子无限期运行 - 无限循环

如何在反应中使用带有useState钩子的回调[重复]

使用 prevState 和 useState 钩子更新对象内部数组中的对象

为啥在反应的“useState”钩子中一遍又一遍地设置初始状态

关于在反应功能组件中读取文件内容和useState钩子[重复]