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

Firebase与Swift:如何检测itemName值在多日期节点中重复存在?

Solution to Detect Duplicate Item Names Across Multiple Date Nodes in Firebase + Swift

Hey there! Your initial idea of collecting all itemName values and checking their occurrence across dates is totally on the right track—let's fix the code and make it work properly.

First, let's break down why your current attempt isn't working: when you call .child("itemName") directly under /Items, Firebase is looking for a single node named itemName at that level, but your itemName fields are nested under each date node, then under auto-generated child IDs. So we need to traverse those layers properly.

Step-by-Step Implementation

Here's how to collect all itemName values along with their associated dates, then check if a target item (like "Milk") exists in 2+ dates:

guard let userId = Auth.auth().currentUser?.uid else { 
    print("User not logged in")
    return 
}

// Reference to the user's Items node
let itemsRef = Database.database().reference().child("users/\(userId)/Items")

itemsRef.observeSingleEvent(of: .value) { snapshot in
    // Dictionary to track each item and the set of dates it appears in
    var itemDateMap = [String: Set<String>]()
    
    // First, iterate over all date nodes (e.g., "Sunday, Oct 10, 2021")
    for dateSnapshot in snapshot.children {
        guard let dateChild = dateSnapshot as? DataSnapshot,
              let dateKey = dateChild.key as String? else { continue }
        
        // Then iterate over all auto-generated child nodes under the date
        for itemSnapshot in dateChild.children {
            guard let itemChild = itemSnapshot as? DataSnapshot,
                  let itemDict = itemChild.value as? [String: Any],
                  let itemName = itemDict["itemName"] as? String else { continue }
            
            // Add the date to the item's set of dates
            if var dates = itemDateMap[itemName] {
                dates.insert(dateKey)
                itemDateMap[itemName] = dates
            } else {
                itemDateMap[itemName] = [dateKey]
            }
        }
    }
    
    // Now check if your target item exists in 2+ dates
    let targetItem = "Milk"
    if let datesForItem = itemDateMap[targetItem], datesForItem.count >= 2 {
        print("✅ '\(targetItem)' exists in \(datesForItem.count) different dates: \(datesForItem)")
    } else {
        print("❌ '\(targetItem)' doesn't exist in multiple dates")
    }
}

Key Notes:

  • We use a [String: Set<String>] dictionary to track each item and the unique dates it appears in (using a Set ensures we don't count duplicate entries within the same date).
  • We traverse two levels deep: first all date nodes, then all auto-ID nodes under each date to extract itemName.
  • The code includes optional binding to safely unwrap snapshots and values, which helps avoid crashes from unexpected data structures.

Optimization for Large Datasets

If your user has a huge number of items/dates, fetching all data at once might be inefficient. A better long-term approach is to add a reverse index to your database structure when writing items:

users -> [userId] -> 
  Items -> [date] -> [autoId] -> itemName: "Milk"
  ItemIndex -> "Milk" -> [date1, date2]  // Maintain this when adding/deleting items

With this index, you can directly check the count of dates for "Milk" with a single query, without fetching all items:

let itemIndexRef = Database.database().reference().child("users/\(userId)/ItemIndex/Milk")
itemIndexRef.observeSingleEvent(of: .value) { snapshot in
    if let dates = snapshot.value as? [String], dates.count >= 2 {
        print("✅ 'Milk' exists in multiple dates")
    }
}

Just remember to update this index every time you add/delete an item (e.g., when adding a "Milk" item on a new date, push the date to ItemIndex/Milk; when deleting, remove the date from the index).

Hope this helps you solve the problem! 😊

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

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.04.30 16:57:48