为什么Redux reducer上的计时器会帮助触发重新渲染

时间:2020-09-10 10:49:11

标签: javascript reactjs redux react-redux

我遇到了一些奇怪的行为,我会更安全地理解

下面是我的减速器的代码。我不明白为什么,但是使用此代码,与redux状态相关联的组件不会重新呈现。我可以使用开发人员工具告知状态已正确更新。

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,
      }
}

与我的reducer中的其他操作相比,我最终猜想该操作的时间成本有些问题,其他一些更复杂的操作似乎效果更好...

所以我添加了一个计时器

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

繁荣,成功了!

我真的不喜欢这种高度hacky的解决方案。

是否有人对正在发生的事情以及如何更好地解决这一问题有任何了解。

注意:

  • 我正在研究本机反应,但似乎没有关联
  • 在组件中,通过useSelector钩子来选择redux状态
const items = useSelector((state) => state.items.allItems)

2 个答案:

答案 0 :(得分:2)

“ allItems.unshift(action.item)”将数据直接添加到减速器状态,因为allItems被引用到redux状态变量。因此,在返回状态之前,您要更新减速器。返回状态后,redux数据将保持不变,因此不会重新呈现组件。

为更好地理解,请参考此答案https://stackoverflow.com/a/48819216/7822241

答案 1 :(得分:0)

在Mohan Krisgna Sai的帮助下,这就是解决方案。

我确实是在不知道状态的情况下对其进行了突变,因为当您将变量分配给引用类型(即对象)时,该变量仅保存对对象实际存储位置的引用,而不是对实际对象的存储位置的引用。对象本身。 这里的更多详细信息:https://stackoverflow.com/a/50840423/13337619

所以,这正在改变状态

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

解决方案很简单:

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