将Firebase中多个词典的值添加到Int

时间:2019-04-01 17:45:40

标签: arrays swift firebase dictionary firebase-realtime-database

我正在使用Firebase存储我的应用中每个视频的观看次数。我想要的是从一个用户那里收集所有视频的所有视图,并显示视图总数。但是我在提取数据并将所有字典值放到Int / String中时遇到了问题!

到目前为止,我已经尝试了许多不同的解决方案,但是我还是将所有不同的值都放在字典的数组/值中,而不是将所有值都添加到一个值中

这是我的代码,用于获取特定用户的所有视频视图,到目前为止没有任何问题。当我打印“ intConvert”时,我会得到不同行中的所有视图。


      let ref = Database.database().reference().child("videoviews").child(stringUid)
    ref.observe(.value, with: { (snapshot) in
        if let dictionary = snapshot.value as? [String: AnyObject]{

            let numbOfViews = dictionary["views"] as! String
            let intConvert = Int(numbOfViews)!
            let ArrayViews = [intConvert]

这是我的数据库结构:

   **videoviews**
        -Lb52VxrEqdSRGljJdP7
                          views: "25"

        -Lb53ARq_lOHEbTruW8s
                          views: "273"

        -Lb53A_cEyX3CYc4mKYn
                          views: "38"

编辑:如果我执行print(dictionary),则来自“ if let dictionary = snapshot.value as?[[String:Anyobject]]的字典如下:

      ["views": 642]
      ["views": 660]
      ["views": 628]
      ["views": 630]
      ["views": 615]
      ["views": 3]
      ["views": 0]
      ["views": 2]
      ["views": 1]

编辑:(我很困惑,忘了添加手镯,对此感到抱歉。) 当我“打印(dictionary.values)时,控制台看起来像这样(来自不同字典的键值):

  [642]
  [660]
  [628]
  [630]
  [615]
   [3]
   [0]
   [2]
   [1]

然后我尝试将其组合成这样的循环:


       var bLoader = 0.0
            for hejArray in 0...ArreyViews.count-1{
                bLoader += Double(Arrej[hejArray])
            }

但是当我打印“ bLoader”时,我仍然获得每个视频在不同行中的所有视图,而不是聚集在一个值中。

那么我需要怎么做才能将Firebase中不同词典中的所有值汇总到一个变量中?

我非常感谢我能为此提供的所有帮助,我可以想象它应该不会太难,但是我会错过一些东西。

编辑 ///我终于找到了问题。我传入的“ StringUid”具有不同数量的值,因此,如果用户的视频数量为9,则整个函数将被调用9次。最终有效的解决方案如下所示:

全局数组声明:

              var myArray = [String]()

在函数内部:

       if let dictionary = snapshot.value as? [String: AnyObject]{
            let numbOfViews = dictionary["views"] as! String
            let intConvert = Int(numbOfViews)!
            self.myArray.append(numbOfViews)
            let intArray = self.myArray.map { Int($0)!} 
            let total = intArray.reduce(0, +)
            self.totalViewsShower2.text = String(total)

提前谢谢!

2 个答案:

答案 0 :(得分:0)

更新

如果您可以像这样直接从字典中打印值,那么解决方案可能就像

一样简单
let total = dictionary.values.reduce(0, +)

或者如果值是字符串,则需要将它们转换为Int

let total = dictionary.values.reduce(0) {sum, value -> Int in return sum + (Int(value) ?? 0)}

如果它们的值是字符串,但定义为Any,则需要额外的转换

let total2 = dictionary2.values.reduce(0) {sum, value -> Int in
    if let str = value as? String {
        return sum + (Int(str) ?? 0)
    }
    return 0
}    

我不确定您的词典中包含什么,但是我认为是这样的

let dictionary: [String: Any] = ["views": ["1", "2", "3"]]

然后,您可以将“ views”键的值转换为String数组,然后在该数组上使用reduce以获取总和

let array = dictionary["views"] as! [String]
let total = array.reduce(0) {sum, value -> Int in return sum + (Int(value) ?? 0)}

答案 1 :(得分:0)

根据您的数据库结构,看起来像这样

{
    "videoviews": {
        "Lb52VxrEqdSRGljJdP7": {
            "views": "25"
        },
        "Lb53ARq_lOHEbTruW8s": {
            "views": "273"
        },
        "Lb53A_cEyX3CYc4mKYn": {
            "views": "38"
        }
    }
}
 let ref = Database.database().reference().child("videoviews").child(stringUid)
    ref.observe(.value, with: { (snapshot) in

        if let dictionary = snapshot.value as? [String: AnyObject] {
            let viewsArray = dictionary.values
                            .compactMap { $0 as? [String: String] }
                            .compactMap { Int($0["views"] ?? "") }

            let totalViews = viewsArray.reduce(0, +)
        }
})