Redux:在 reducer 中过滤数据数组的正确方法是什么?
Redux: what is the correct way to filter a data array in reducer?
我想在搜索时过滤一个数组 SEARCH_TEXT 是一个更改操作
我感到困惑的是我如何 return 当按下删除键并且文本现在变为空时的状态,我想我可以在 else 语句中使用初始状态但我的倾向是这是错误的?当我 return 只是声明它已经准备好在 if 语句中被操纵时。
简单的例子。
提前致谢。
const initialState = ['hello', 'wahhh', 'yo'];
export default function searchSimple(state = initialState, action) {
switch (action.type) {
case SEARCH_TEXT:
if(action.text.length > 0){
return state.filter(item =>
item.startsWith(action.text)
)
}
else {
return state
}
永远记住,状态是你的 "source of truth"。小心基于临时过滤器消除状态。一旦你这样做,那些项目就消失了。 (让他们回来的唯一方法是将你的状态重置为 initialState,这可能并不理想。)
更好的方法是按原样保留您的项目列表,并简单地存储搜索文本。
const initialState = {
searchText: '',
items: [ 'hello', 'wahhh', 'yo' ]
};
export default function searchSimple(state = initialState, action) {
switch (action.type) {
case SEARCH_TEXT:
return Object.assign({}, state, {
searchText: action.text
});
}
}
虽然您的状态不会包含过滤列表,但它会告诉您构建过滤列表所需知道的一切。
假设您使用的是 React,您的 "smart component" 可以使用以下 mapStateToProps()
函数进行设置:
function mapStateToProps(state) {
const { items, searchText } = state.searchSimple;
return {
filteredItems: items.filter((item) => item.startsWith(searchText))
};
}
如果您需要在多个地方使用此过滤列表,请考虑创建一个 "selector" 函数,如 Redux 购物车示例中所示。
https://github.com/reactjs/redux/blob/master/examples/shopping-cart/src/reducers/cart.js
看起来像这样:
export function filteredItems(state) {
const { items, searchText } = state.searchSimple;
return items.filter((item) => item.startsWith(searchText));
}
有关选择器的更高级方法,请查看重新选择库。
IMO,过滤数据的正确位置不是直接在 reducers 中,而是在 selectors.
来自 redux 文档:
Reselect is a simple library for creating memoized, composable selector functions. Reselect selectors can be used to efficiently compute derived data from the Redux store.
我目前正在使用选择器来过滤和排序数据。
- 状态下无数据重复。您不必存储已过滤项目的副本。
- 可以在不同的组件中使用相同的数据,例如,每个组件使用不同的过滤器。
- 您可以使用应用程序中已有的选择器组合应用许多数据计算的选择器。
- 如果你做对了,你的选择器将是纯函数,那么你可以很容易地测试它们。
- 在多个组件中使用相同的选择器。
我想在搜索时过滤一个数组 SEARCH_TEXT 是一个更改操作 我感到困惑的是我如何 return 当按下删除键并且文本现在变为空时的状态,我想我可以在 else 语句中使用初始状态但我的倾向是这是错误的?当我 return 只是声明它已经准备好在 if 语句中被操纵时。
简单的例子。
提前致谢。
const initialState = ['hello', 'wahhh', 'yo'];
export default function searchSimple(state = initialState, action) {
switch (action.type) {
case SEARCH_TEXT:
if(action.text.length > 0){
return state.filter(item =>
item.startsWith(action.text)
)
}
else {
return state
}
永远记住,状态是你的 "source of truth"。小心基于临时过滤器消除状态。一旦你这样做,那些项目就消失了。 (让他们回来的唯一方法是将你的状态重置为 initialState,这可能并不理想。)
更好的方法是按原样保留您的项目列表,并简单地存储搜索文本。
const initialState = {
searchText: '',
items: [ 'hello', 'wahhh', 'yo' ]
};
export default function searchSimple(state = initialState, action) {
switch (action.type) {
case SEARCH_TEXT:
return Object.assign({}, state, {
searchText: action.text
});
}
}
虽然您的状态不会包含过滤列表,但它会告诉您构建过滤列表所需知道的一切。
假设您使用的是 React,您的 "smart component" 可以使用以下 mapStateToProps()
函数进行设置:
function mapStateToProps(state) {
const { items, searchText } = state.searchSimple;
return {
filteredItems: items.filter((item) => item.startsWith(searchText))
};
}
如果您需要在多个地方使用此过滤列表,请考虑创建一个 "selector" 函数,如 Redux 购物车示例中所示。 https://github.com/reactjs/redux/blob/master/examples/shopping-cart/src/reducers/cart.js
看起来像这样:
export function filteredItems(state) {
const { items, searchText } = state.searchSimple;
return items.filter((item) => item.startsWith(searchText));
}
有关选择器的更高级方法,请查看重新选择库。
IMO,过滤数据的正确位置不是直接在 reducers 中,而是在 selectors.
来自 redux 文档:
Reselect is a simple library for creating memoized, composable selector functions. Reselect selectors can be used to efficiently compute derived data from the Redux store.
我目前正在使用选择器来过滤和排序数据。
- 状态下无数据重复。您不必存储已过滤项目的副本。
- 可以在不同的组件中使用相同的数据,例如,每个组件使用不同的过滤器。
- 您可以使用应用程序中已有的选择器组合应用许多数据计算的选择器。
- 如果你做对了,你的选择器将是纯函数,那么你可以很容易地测试它们。
- 在多个组件中使用相同的选择器。