在反应中,我想知道是否有办法测试反应键是否是唯一的。我有一系列我正在展示的专辑,这些是从mongodb中提取出来的。设置数据库的方式,数据库可以包含重复的条目,是的,它必须是这种方式,不,我不是在寻找一种方法来删除数据库查询中的重复项。希望在做出反应。
当您向下滚动页面时,客户端一次加载来自数据库的20个结果,在您继续滚动时根据用户生成的查询获取接下来的20个结果。最终,您将遇到这些重复项,并且react会生成唯一的键警告,因为唯一键是ID字符串。
this.props.data.map( album => {
album.cover = (album.images[0]) ? album.images[0].url : null
return <Album data={album} key={album.sid} />
})
我想知道是否有办法测试已经渲染的反应键的album.sid
属性,如果已经渲染了键,则不渲染组件并移动到下一个。
答案 0 :(得分:2)
您可以在操作创建器(或者如果您不使用Redux时返回API调用的结果的位置),reducer或组件中过滤重复项,如果您仍希望将其保留在Redux中无论出于何种原因。
O(n)重复过滤算法将是:
const seen = new Set();
const uniqueData = data.filter(({ sid }) => {
if (seen.has(sid)) {
return false;
}
seen.add(sid);
return true;
});
如果您决定在组件级别执行此操作,则可能需要考虑使用某些memoization library,以便仅在组件重新呈现时data
已更改时才重新计算过滤
答案 1 :(得分:0)
从我关于redux的评论(已删除)中回答此评论:
但是reducer会如何针对传入的结果检查已经加载的结果?你能用模拟的例子发一个答案吗?
使用哈希表:
const DEFAULT_STATE = {
byId: [],
byHash: {}
}
export default function (state = DEFAULT_STATE, action) {
switch (action.type) {
case GET_ALBUM:
return {
...state,
byId: state.byId.includes(action.payload.id)
? [ ...state.byId ]
: [ ...state.byId, action.payload.id ],
byHash: {
...state.byHash,
[action.payload.id]: action.payload
}
}
default:
return state
}
}
你的组件:
this.props.albumIds.map( id => {
let album = this.props.albums[id]
album.cover = (album.images[0]) ? album.images[0].url : null
return <Album data={album} key={album.sid} />
})
假设mapStateToProps
喜欢:
{
albumIds: state.albums.byId,
albums: state.albums.byHash
}