React Native中FlashList点击已选复选框报错Cannot read property 'x' of undefined
解决FlashList点击复选框报错
Cannot read property "x" of undefined的问题 核心原因分析
报错本质是OrderCard组件接收到了undefined的data属性,进而在内部访问对应属性时抛出错误。根源集中在这几点:
orders.find(...)!的非空断言强制忽略了找不到对应订单的情况,当FlashList更新过程中短暂渲染已移除的项时,find返回undefined,直接传给OrderCard就会触发报错。extraData传递了包含setScheduleData的对象,每次渲染都会生成新对象,导致FlashList不必要的重渲染,加剧数据不同步问题。- 可能存在
scheduleData的更新不是完全不可变的情况,导致FlashList无法正确感知数据变化,渲染旧数据。
分步解决方案
修复
orders.find的非空判断
去掉非空断言,先检查是否找到对应订单,避免传递undefined给OrderCard:renderItem={({ item, index }) => { const order = orders.find(({ id }) => id === item); if (!order) return null; // 或渲染占位组件,比如<View /> return ( <OrderCard data={order} index={index} scheduleData={scheduleData} setScheduleData={setScheduleData} /> ); }}简化
extraData的依赖extraData只需要传递会变化的状态scheduleData即可,setScheduleData是稳定的函数引用,不需要作为依赖:extraData={scheduleData}确保
scheduleData的不可变更新
更新状态时要保证内外层数组都是新的引用,避免直接修改原数组:const handleToggle = (itemId) => { setScheduleData(prev => { // 复制外层数组 const newSchedule = [...prev]; // 复制内层目标数组,避免直接修改原数组 const innerArr = newSchedule[1] ? [...newSchedule[1]] : []; const idx = innerArr.indexOf(itemId); if (idx !== -1) { innerArr.splice(idx, 1); // 移除项 } else { innerArr.push(itemId); // 添加项 } newSchedule[1] = innerArr; return newSchedule; }); };给
data属性加默认值
防止scheduleData[1]为undefined导致data出错:data={[...(scheduleData[1] || [])]}
修改后的完整FlashList代码
<FlashList data={[...(scheduleData[1] || [])]} estimatedItemSize={256} extraData={scheduleData} renderItem={({ item, index }) => { const order = orders.find(({ id }) => id === item); if (!order) return null; return ( <OrderCard data={order} index={index} scheduleData={scheduleData} setScheduleData={setScheduleData} /> ); }} />
内容的提问来源于stack exchange,提问作者Henry
相关产品推荐
相关产品推荐

