React中使用useMemo后帖子不显示?技术求助
问题:useMemo缓存帖子列表后页面无内容显示
开发论坛React组件时,为避免图标更新导致帖子重渲染,尝试用useMemo缓存帖子列表,但页面本该显示帖子的区域完全为空。
原代码:
const postMapping = () => {props.listOfPosts.map((post, index) => { return ( <div key={post.title} ind={index.toString()} className='postContainer'> <div className='postTitle'>{post.title}</div> <div className='postContent'> {post.content.slice(0, props.charLimit)}{post.content.length > props.charLimit ? <span className='postMore curHover' onClick={e => showMore(e)}> DEVAMI...</span> : ""} </div> <div className='postIconContainer'> <img className='backgroundGrey commentImg curHover' src={icons.comment} alt="comments" /> <div className='commentAmount amount'>{post.commentAmount}</div> <img className='backgroundGrey heartImg curHover' src={icons.heartEmpty} alt="heart" onClick={e => changeUpvoteIcon(e)}/> <div className='likeAmount amount'>{post.likeAmount}</div> </div> </div>); })} const listOfPosts = useMemo(() => postMapping, [props.listOfPosts]); return ( <div id="postSectionContainer"> {listOfPosts} </div> );
错误原因:
useMemo的回调函数返回的是postMapping函数本身,而非调用该函数生成的JSX元素数组。React渲染时无法识别未执行的函数,因此页面无内容。另外,postMapping还依赖props.charLimit、showMore、changeUpvoteIcon等变量,但这些未加入useMemo的依赖数组,后续这些值变化时缓存内容不会更新,会引发逻辑异常。
修复方案:
- 在
useMemo回调中调用postMapping(),返回实际的JSX数组 - 补充
useMemo的依赖数组,加入所有postMapping用到的外部变量 - 优化写法:直接在
useMemo回调中编写map逻辑,避免额外函数的混淆
修复后的代码:
const listOfPosts = useMemo(() => { return props.listOfPosts.map((post, index) => { return ( <div key={post.title} ind={index.toString()} className='postContainer'> <div className='postTitle'>{post.title}</div> <div className='postContent'> {post.content.slice(0, props.charLimit)}{post.content.length > props.charLimit ? <span className='postMore curHover' onClick={e => showMore(e)}> DEVAMI...</span> : ""} </div> <div className='postIconContainer'> <img className='backgroundGrey commentImg curHover' src={icons.comment} alt="comments" /> <div className='commentAmount amount'>{post.commentAmount}</div> <img className='backgroundGrey heartImg curHover' src={icons.heartEmpty} alt="heart" onClick={e => changeUpvoteIcon(e)}/> <div className='likeAmount amount'>{post.likeAmount}</div> </div> </div>); }) }, [props.listOfPosts, props.charLimit, showMore, changeUpvoteIcon]); return ( <div id="postSectionContainer"> {listOfPosts} </div> );
内容的提问来源于stack exchange,提问作者Bot Ellis
相关产品推荐
相关产品推荐

