更改Firebase观察器SWIFT 4后返回函数

时间:2019-03-01 14:25:01

标签: swift firebase firebase-realtime-database observers

我正在重写firebase函数,以便将实时数据从数据库中放入自己的函数中,因此在引用数据库时从table(df$seq) # AAGTCA AGCCTCA AGTCA AGTCAGG # 1 1 2 1 table(df$grouping) # 1 2 3 4 # 1 1 2 1 sort(table(df$seq), decreasing = T) # AGTCA AAGTCA AGCCTCA AGTCAGG # 2 1 1 1 更改为.observe(.childAdded, with: {(snapshot) in。该函数现在比以前更早在.observeSingleEvent(of: .value, with: { (snapshot) in上返回。 快照相同时发生了什么变化?关于它的任何解释都很棒,因为我自己看不到它。 一如既往的感谢。

以下是该函数的两个版本:

老观察员:

guard let data = snapshot.value as? [String :String] else { return }

新观察者:

func displayAlerts(setCompletion: @escaping (Bool) -> ()) {
        self.mapView.removeAnnotations(mapView.annotations)
        MapArray.alertNotificationCoordinatesArray.removeAll()
        self.userAlertNotificationArray.removeAll()
        print("                     MapArray.alertNotificationCoordinatesArray before snapshot is: \(MapArray.alertNotificationCoordinatesArray)")
        print("                     self.userAlertNotificationArray before snapshot is: \(self.userAlertNotificationArray)")

        ref = Database.database().reference()

        databaseHandle = ref?.child("Continent").child("Europe").child("Country").child("Italy").child("Region").child("Emilia-Romagna").child("City").child("Bologna").child("Community").child("Alert Notifications").observe(.childAdded, with: { (snapshot) in


            //            self.mapView.removeAnnotations(self.mapView.annotations) //
            print("         snapshot is: \(snapshot)")
            guard let data = snapshot.value as? [String:String] else { return }
            guard let firebaseKey = snapshot.key as? String else { return }
            //                let date = data!["Date"]
            //                let time = data!["Time"]
            let dataLatitude = data["Latitude"]!
            let dataLongitude = data["Longitude"]!

            let type = data["Description"]!
            let id = Int(data["Id"]!)
            let doubledLatitude = Double(dataLatitude)
            let doubledLongitude = Double(dataLongitude)
            let recombinedCoordinate = CLLocationCoordinate2D(latitude: doubledLatitude!, longitude: doubledLongitude!)

            print("Firebase alerts posts retrieved")

            let userAlertAnnotation = UserAlert(type: type, coordinate: recombinedCoordinate, firebaseKey: firebaseKey, title: type,id: id!)

            self.userAlertNotificationArray.append(userAlertAnnotation)  // array of notifications coming from Firebase
            //            print("userAlertNotificationArray after retrieving from Firebase is : \(self.userAlertNotificationArray)")

            MapArray.alertNotificationCoordinatesArray.append(recombinedCoordinate) // array for checkig alerts on route


            print("                 MapArray.alertNotificationCoordinatesArray after snapshot is: \(MapArray.alertNotificationCoordinatesArray)")
            print("                     self.userAlertNotificationArray after snapshot is: \(self.userAlertNotificationArray)")
            setCompletion(true)
            self.mapView.addAnnotations(self.userAlertNotificationArray)
        })

    }

编辑:

以下是快照中的照片,以便查看两个版本的结果:

observeSingleEvent快照:

func displayAlerts(setCompletion: @escaping (Bool) -> ()) {
    print("                     MapArray.alertNotificationCoordinatesArray before newer displayAlert snapshot is: \(MapArray.alertNotificationCoordinatesArray)")
    print("                     self.userAlertNotificationArray before displayAlert snapshot is: \(self.userAlertNotificationArray)")

    if self.userAlertNotificationArray.count == 0 {
       ref = Database.database().reference()

        ref?.child("Continent").child("Europe").child("Country").child("Italy").child("Region").child("Emilia-Romagna").child("City").child("Bologna").child("Community").child("Alert Notifications").observeSingleEvent(of: .value, with: { (snapshot) in


            //            self.mapView.removeAnnotations(self.mapView.annotations) //
            print("         snapshot is: \(snapshot)")
            guard let data = snapshot.value as? [String :Any] else { return }
            guard let firebaseKey = snapshot.key as? String else { return }
            //                let date = data!["Date"]
            //                let time = data!["Time"]
            let dataLatitude = data["Latitude"] as! Double
            let dataLongitude = data["Longitude"] as! Double

            let type = data["Description"] as! String
            let id = Int(data["Id"] as! String)
            let doubledLatitude = Double(dataLatitude)
            let doubledLongitude = Double(dataLongitude)
            let recombinedCoordinate = CLLocationCoordinate2D(latitude: doubledLatitude, longitude: doubledLongitude)

                        print("Firebase alerts posts retrieved")

            let userAlertAnnotation = UserAlert(type: type, coordinate: recombinedCoordinate, firebaseKey: firebaseKey, title: type,id: id!)

            self.userAlertNotificationArray.append(userAlertAnnotation)  // array of notifications coming from Firebase

            MapArray.alertNotificationCoordinatesArray.append(recombinedCoordinate) // array for checkig alerts on route


            print("                 MapArray.alertNotificationCoordinatesArray after newer displayAlert snapshot is: \(MapArray.alertNotificationCoordinatesArray)")
            print("                     self.userAlertNotificationArray after newer displayAlert snapshot is: \(self.userAlertNotificationArray)")
            self.mapView.addAnnotations(self.userAlertNotificationArray)
            setCompletion(true)

        })
    }
}

和childAdded快照:

snapshot is: Snap (Alert Notifications) {
    "-LZtTuFSKMhhXFwyT-7K" =     {
        Description = "Ciclabile chiusa";
        Id = 0;
        Latitude = "44.50139187990401";
        Longitude = "11.33592981426992";
    };
    "-LZtUV8MOxVrvPnEfi4g" =     {
        Description = "Lavori in corso";
        Id = 1;
        Latitude = "44.5013918797401";
        Longitude = "11.335929814371545";
    };
    "-LZtV7sJJrOQjAimszTm" =     {
        Description = "Pericoli sulla ciclabile";
        Id = 2;
        Latitude = "44.50139187974223";
        Longitude = "11.335929814367324";
    };
}

3 个答案:

答案 0 :(得分:1)

更改

visibility: initial;

guard let data = snapshot.value as? [String :String] else { return }

答案 1 :(得分:0)

您能举例说明json如何在数据库中存储吗?与

.observe(.childAdded, with: {(snapshot) in

您只会收到添加的孩子,并且

.observeSingleEvent(of: .value, with: { (snapshot) in

您收到了整个节点,因此该节点可能不是[String:String],可能不止一个项目,因此应该是[String:Any],然后您可以从中获得每个孩子。

答案 2 :(得分:0)

这只是部分答案,但经过多次尝试,并在Sh_Khan的帮助下,我们使其成功了。问题出在guard let data = snapshot.value as? [String :Any] else { return }行中,该行需要为guard let data = snapshot.value as? [String : [String : String] else { return }

因此该函数必须编写为:

func displayAlerts(setCompletion: @escaping (Bool) -> ()) {
        print("                     MapArray.alertNotificationCoordinatesArray before displayAlert snapshot is: \(MapArray.alertNotificationCoordinatesArray)")
        print("                     self.userAlertNotificationArray before displayAlert snapshot is: \(self.userAlertNotificationArray)")

        if self.userAlertNotificationArray.count == 0 {
           ref = Database.database().reference()

            ref?.child("Continent").child("Europe").child("Country").child("Italy").child("Region").child("Emilia-Romagna").child("City").child("Bologna").child("Community").child("Alert Notifications").observeSingleEvent(of: .value, with: { (snapshot) -> Void in
                print("         snapshot is: \(snapshot)")
                guard let data = snapshot.value as? [String :[String:String]] else { return }

                guard let firebaseKey = snapshot.key as? String else { return }

                data.values.forEach {
//                    let firebaseKey = data.keys[]

                    let dataLatitude = $0["Latitude"]!
                    let dataLongitude = $0["Longitude"]!
                    let type = $0["Description"]!
                    let id = Int($0["Id"]!)

                    print("firebaseKey is:\(firebaseKey)")
                    print("dataLatitude is: \(dataLatitude)")
                    print("dataLongitude is: \(dataLongitude)")
                    print("type is: \(type)")
                    print("id is: \(id)")
                    print("Key is: \(firebaseKey)")
                    print("data is: \(data)")

                    let doubledLatitude = Double(dataLatitude)
                    let doubledLongitude = Double(dataLongitude)
                    let recombinedCoordinate = CLLocationCoordinate2D(latitude: doubledLatitude!, longitude: doubledLongitude!)

                    let userAlertAnnotation = UserAlert(type: type, coordinate: recombinedCoordinate, firebaseKey: firebaseKey, title: type,id: id!)
                    self.userAlertNotificationArray.append(userAlertAnnotation)  // array of notifications coming from Firebase
                    MapArray.alertNotificationCoordinatesArray.append(recombinedCoordinate)
                }


                            print("Firebase alerts posts retrieved")

                print("                 MapArray.alertNotificationCoordinatesArray after  displayAlert snapshot is: \(MapArray.alertNotificationCoordinatesArray)")
                print("                     self.userAlertNotificationArray after  displayAlert snapshot is: \(self.userAlertNotificationArray)")
                self.mapView.addAnnotations(self.userAlertNotificationArray)
                setCompletion(true)

            })
        }
    }

现在我有两件事要解决。第一:如何获得子键,因为行guard let firebaseKey = snapshot.key as? String else { return }为我提供了节点的名称? 第二:我创建的仅用于通过.observe(.childAdded, with: { (snapshot) in获取newerAlerts的较新函数不会在将新的子级添加到节点时被调用。 我应该问新问题还是继续此处?

谢谢