You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

React数组元素覆盖问题:添加元素后除新增项外均重复

解决Firestore onSnapshot导致数组元素重复的问题

看起来你遇到的核心问题是Firestore的onSnapshot监听每次触发时,都会往同一个数组里追加数据,最终导致数组元素重复。我来帮你分析下问题根源,再给出修复方案:

问题原因

你的datesArray是在useEffect的作用域内定义的,只初始化一次。但onSnapshot是持续监听数据变化的回调——每次数据库数据更新,这个回调都会执行,而你一直在往同一个datesArray里push新数据,最后设置到state里的自然就是累积了多轮数据的重复数组。之前尝试调用setArray([])没用,是因为清空状态后,下一次快照回调又会把累积的数组重新赋值回去。

修复方案

这里有三个关键修改点:

  • 每次快照触发时重新初始化数组:把datesArray的定义移到onSnapshot回调内部,确保每次数据更新都用全新的数组存储当前快照内容
  • 补充useEffect的依赖项:你的查询依赖了object.id和props.date,必须把它们加入依赖数组,否则这些值变化时,监听的还是旧的查询条件
  • 清理Firestore监听:onSnapshot会返回一个取消订阅的函数,在组件卸载或依赖变化时调用它,避免内存泄漏

修改后的完整代码

const [array, setArray] = useState([])
const [loading, setLoading] = useState(false)

useEffect(() => {
  setLoading(true)
  const objectRef = firebase.firestore().collection('obiekt').doc(object.id)
  let startDay = new Date(props.date);
  let endDay = new Date(props.date);
  startDay.setHours(0, 0, 0, 0);
  endDay.setHours(23, 59, 59, 999);

  // 获取取消订阅函数,用于后续清理
  const unsubscribe = firebase.firestore().collection("wydarzenie")
    .where('obiekt', '==', objectRef)
    .where('data_rozpoczecia', '>=', startDay)
    .where('data_rozpoczecia', '<=', endDay)
    .orderBy('data_rozpoczecia')
    .onSnapshot(resp => {
      // 每次快照触发时重新创建空数组,避免累积旧数据
      let datesArray = [];
      resp.docs.forEach(el => { // 这里用forEach比map更合适,因为不需要返回值
        datesArray.push({ ...el.data(), id: el.id })
      })
      setLoading(false)
      setArray(datesArray)
      console.log(datesArray)
    })

  // 组件卸载或依赖变化时,取消Firestore监听
  return () => unsubscribe()
}, [object.id, props.date]) // 补充查询依赖的变量

// 渲染部分
{array && array.map(hour => {
  return (
    <div className={styles.CalendarInfoHour} key={hour.id}>
      {moment(hour.data_rozpoczecia.toDate()).locale('pl').format('LT')}-
      {moment(hour.data_zakonczenia.toDate()).locale('pl').format('LT')} Zajęte
    </div>
  )
})}

额外优化小提示

把resp.docs.map()改成resp.docs.forEach()会更语义化,因为我们只是遍历文档做push操作,不需要利用map返回的新数组~

内容的提问来源于stack exchange,提问作者poldeeek

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.05.07 21:22:43