简体   繁体   English

为什么 Redux 减速器上的计时器有助于触发重新渲染

[英]Why would a timer on a Redux reducer help trigger a re-render

I came across some weird behavior that I would feel safer to understand我遇到了一些奇怪的行为,我会觉得理解这些行为会更安全

Below is the code of my reducer.下面是我的减速器的代码。 I can not get why, but with this code the component tied to the redux state does not re-render .我不明白为什么,但是使用此代码,绑定到 redux 状态的组件不会重新渲染 I can tell with the developper tools that the state is properly updated.我可以通过开发人员工具告诉状态已正确更新。

const initialState = {
  allItems: [],
  favItems: [],
}

export default (state = initialState, action) => {
  let allItems

    case CREATE_ITEM:
      allItems = state.allItems
      allItems.unshift(action.item)
      return {
        ...state,
        allItems: allItems,
      }
}

Comparing with other actions in my reducer, I finally guess that there was something about the time cost of the operation, some other operations a bit more complicated seemed to work better...与我的减速器中的其他操作相比,我终于猜到了操作的时间成本,其他一些稍微复杂一点的操作似乎效果更好......

So I added a timer所以我加了一个计时器

case CREATE_ITEM:
      allItems = state.allItems
      allItems.unshift(action.item)
      setTimeout(() => {
        return {
          ...state,
          allItems: allItems,
        }
      }, 0)

And boom, it worked !繁荣,它奏效了!

I really don't like this highly hacky solution.我真的不喜欢这个高度hacky的解决方案。

Does anyone has any idea about what is happening and how I could solve this in a better way.有没有人知道发生了什么以及我如何以更好的方式解决这个问题。

Notes :注意事项:

  • I'm working on react-native, but it doesn't seem related我正在研究本机反应,但似乎没有关系
  • In the component, the redux state is selected with the useSelector hook在组件中,使用useSelector钩子选择 redux 状态
const items = useSelector((state) => state.items.allItems)

"allItems.unshift(action.item)" adds data directly to the reducer state, because allItems is referenced to redux state variable. "allItems.unshift(action.item)" 将数据直接添加到reducer state,因为allItems 被引用到redux state 变量。 So before returning the state you are updating the reducer.因此,在返回状态之前,您正在更新减速器。 After returning the state there won't be any change in the redux data so component is not getting re-rendered.返回状态后,redux 数据不会有任何变化,因此组件不会被重新渲染。

For better understanding refer to this answer https://stackoverflow.com/a/48819216/7822241为了更好地理解,请参阅此答案https://stackoverflow.com/a/48819216/7822241

Here is the solution, with the help of Mohan Krisgna Sai answer.这是解决方案,在 Mohan Krisgna Sai 的帮助下回答。

I was indeed mutating the state without knowing it, because when you assign a variable to a reference type (ie: an object), the variable only holds a reference to the memory location where the object is actually stored, not the actual object itself.我确实在不知道的情况下改变了状态,因为当您将变量分配给引用类型(即:对象)时,该变量仅保存对实际存储对象的内存位置的引用,而不是实际对象本身。 Further details here : https://stackoverflow.com/a/50840423/13337619此处的更多详细信息: https : //stackoverflow.com/a/50840423/13337619

So, this, is mutating the state所以,这是改变状态

allItems = state.allItems
allItems.unshift(action.item)

The solution is straightforward :解决方案很简单:

    case CREATE_ITEM:
      return {
        ...state,
        allItems: [action.item, ...state.allItems],
      }

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM