我们可以对每个选择器(即使是最简单的 getter)使用 Redux 的 Reselect 记忆吗?

OTm*_*Tmn 2 reactjs redux reselect

我是 Redux 的新手,我一直在阅读有关 Redux 的好东西,包括记忆技术(尤其是重新选择)。我有一个问题,但我很难找到正确的答案。如果我们为每个选择器添加记忆(假设我们有很多),即使是简单的 getter,是否会导致性能问题(可能是由于后台的记忆数据?)?复杂选择器的记忆显然是有益的,因为它可以防止在不需要时重新计算。但我发现简单选择器的记忆也很有用,可以避免无用的重新渲染。

事实上,我使用 useSelector 钩子并且文档指出:

当一个动作被调度时,useSelector()将对前一个选择器结果值和当前结果值进行引用比较。如果它们不同,组件将被强制重新渲染。如果它们相同,则组件将不会重新渲染。

因此,即使对于返回相同原始值(比如 int)的选择器,如果我没有错的话,useSelector 应该始终使组件重新渲染(即使选择器总是返回相同的值)。

如果我说的是真的,那么记住即使是简单的 getter 对此也是有用的,但是过度使用它会导致其他性能问题吗?

感谢您的帮助

mar*_*son 8

编写记忆化的选择器函数很有用,但许多人试图记忆太多实际上不应该记忆的选择器

如果选择器函数只是执行简单的查找并从状态返回现有数据,则无需记住它 - 它可能只是一个简单的函数。例如:

const selectTodoById = (state, id) => state.todos.entities[id];
Run Code Online (Sandbox Code Playgroud)

其次,您可能也不应该为每个状态字段创建单独的选择器。找到合理的粒度级别。

仅当选择器返回一些派生数据时,记忆选择器才有用。一个很好的例子是过滤数组:

const selectCompletedTodos = createSelector(
  state => state.todos,
  state => state.filters.completed,
  (todos, completed) => todos.filter(t => t.completed === completed)
);
Run Code Online (Sandbox Code Playgroud)

这样,只有当输入值发生变化时,才会重新计算派生数据。

作为旁注,我实际上计划编写一个新的 Redux 核心文档页面,其中包含有关何时以及如何编写记忆选择器的指导和使用信息。在那之前,您可以阅读我的文章《使用重新选择选择器进行封装​​和性能》,其中已经涵盖了很多相关内容。