React Native使用Redux作为FlatList数据源,状态更新后未重渲染问题
问题原因
- 字段不匹配:reducer处理
REFRESH_GOOGLE_PLACES动作时,更新的是userGPlacesFiltered字段,但mapStateToProps中组件订阅的是state.rdx_userGPlaces,两者完全不对应。修改的状态字段没有被组件监听,组件props不会触发更新,FlatList自然不会重新渲染。 - 不可变更新缺失:如果传入reducer的
gpArray还是原来的数组引用(比如仅修改了数组内对象的属性,没有生成新的数组实例),Redux的浅比较会认为状态没有变化,不会触发订阅更新。 - FlatList配置缺失:FlatList本身是PureComponent,默认只会在
data属性的引用变化时重渲,如果没有配置keyExtractor或者渲染依赖额外参数,也会导致不重渲。
解决方案
- 修正reducer更新的字段,和组件订阅的字段保持一致:
如果你组件使用的是rdx_userGPlaces,把reducer里的更新字段改为对应名称即可:case REFRESH_GOOGLE_PLACES: return {...state, rdx_userGPlaces: action.payload}; - 严格遵守Redux不可变更新原则,更新数组时生成新的数组实例:
调用_actRefreshGPArray传参时,不要直接修改原数组后传入,要生成新数组,比如修改数组内某一项的属性时可以这么写:const newGpArray = oldArray.map(item => { if (item.id === targetId) { // 生成新的对象实例,修改对应属性 return {...item, changedProp: newValue}; } return item; }) // 把新数组传给action dispatch(_actRefreshGPArray(newGpArray)) - 给FlatList补充必要配置:
加上keyExtractor保证每一项的key唯一,如果渲染逻辑还有额外依赖参数,同时加上extraData属性:<FlatList data={this.props.rdx_userGPlaces} keyExtractor={(item) => item.id.toString()} extraData={this.props.rdx_userGPlaces} // 其余原有配置 />
内容的提问来源于stack exchange,提问作者james murphy
相关产品推荐
相关产品推荐

