本文介绍了您如何正确地从Firebase按时间顺序排序数据的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我试图从Firebase订购我的数据,所以最近的帖子在顶部(如Instagram),但我无法正常工作。我应该使用服务器时间戳吗?是否有createdAt字段?

  func getPosts(){
POST_REF.observeEventType(.Value,withBlock: {$ snapshot中的$ b guard让posts = snapshot.value as?[String:[String:String]] else {
print(No Posts Found)
return
}

Post.feed?.removeAll()
for(postID,post)in posts {
let newPost = Post.initWithPostID(postID,postDict:post)!
Post.feed?.append(newPost)
}
Post.feed?=(Post.feed?.reverse())!
self.tableView.reloadData()
} ,withCancelBlock:{
print(error.localizedDescription)
})
}


解决方案

仅为数组使用 reverse()不足以涵盖所有内容。你需要考虑的事情有很多:
$ b


  • 限制数据检索时,使用 append()然后反向()来节省时间。您不必每次都删除所有数组。

  • >加载


让我们开始吧。您可以为您的帖子 timestamp 日期/时间创建一个子项为全局。为了提供像 Instagram 秒,我建议您使用 UTC时间。所以我会打电话给这个:( timeUTC



要排序所有文章,请使用 since1970 时间戳。所以我会调用这个( timestamp ),然后你可以保留另一个节点为(reversedTimestamp)添加 - 时间戳的前缀。所以当你使用 queryOrdered 这个节点。您可以使用 yourQuery.queryLimited(toFirst:5)处理最新的5个帖子。



在Swift 3中获取timeUTC节点的UTC日期/时间:

  let date = Date()
let formatter = DateFormatter()
formatter.locale = Locale(identifier:en_US_POSIX)
formatter.dateFormat =yyyy-MM-dd HH:mm:ss ZZZ
formatter.timeZone = TimeZone(缩写:UTC)
let utcTimeZoneStr = formatter.string(from:date)

+0000表示现在是世界时,请看 http://time.is/tr/UTC



2.自从1970年以来在Swift 3中对帖子进行排序的时间戳:

  let timestamp =(Date()。timeIntervalSince1970 as NSString).doubleValue 
let reversedTimestamp = -1.0 * timestamp

现在,您可以将它们保存在您的Firebase帖子li上

 posts:{
-KHLOy5mOSq0SeB7GBXv:{
timestamp: 1475858019.2306
timeUTC:2012-02-04 12:11:56 +0000
},
-KHLrapS0wbjqPP5ZSUY:{
timestamp: 1475858010.1245
timeUTC:2014-02-04 12:11:56 +0000
},

我将通过五个邮箱检索五个邮件,所以我在 viewDidLoad 中使用 queryLimited(toFirst:5)

  let yourQuery = ... queryOrdered(byChild:reverseTimestamp)
.queryEnding(atValue:\\ \\(self.pageOnTimestamp),childKey:reverseTimestamp)

yourQuery.observeSingleEvent(:.value,其中:{(snapshot)in

if snapshot.value是NSNull {

print(There is no post。)

}
else {

yourQuery.queryLimited(toFirst: 5).observeSingleEvent(of:.value,with:{(sna ())
$ b self.posts.removeAll(keepingCapacity:true)
$ b $ for(i,snap)in snapshot.children.enumerated(){

如果让postAllDict = snapshot.value为? [String:AnyObject] {
如果让postDict = postAllDict [(作为AnyObject捕捉).key as String] as? (String:AnyObject){

let post = Post(key:(snap as AnyObject).key as String,postDict:postDict)
self.posts.append(post)



$ b完成(true)
})
}
})

如果用户到达最新的帖子,可以使用 willDisplay 方法处理它,然后你可以调用loadMore函数。
$ b $ pre $ func tableView(tableView:UITableView,willDisplay cell:UITableViewCell,forRowAt indexPath:IndexPath){

if self.posts.count - 1 == indexPath.row {
//调用loadMore函数。




在loadMore()函数中,你可以处理最新帖子的时间戳,然后开始 - 结束查询,所以你可以轻松地继续下一个前5个职位,同时追加数组。


I'm trying to order my data from Firebase so the most recent post is at the top (like Instagram), but I just can't get it to work properly. Should I be using a server timestamp? Is there a "createdAt" field?

func getPosts() {
    POST_REF.observeEventType(.Value, withBlock: { snapshot in
        guard let posts = snapshot.value as? [String : [String : String]] else {
            print("No Posts Found")
            return
        }

        Post.feed?.removeAll()
        for (postID, post) in posts {
            let newPost = Post.initWithPostID(postID, postDict: post)!
            Post.feed?.append(newPost)
        }
        Post.feed? = (Post.feed?.reverse())!
        self.tableView.reloadData()
        }, withCancelBlock: { error in
            print(error.localizedDescription)
    })
}
解决方案

Using only reverse() for your array is not enough way to encompass everything. There are different things you need to think about:

  • Limit while retrieving data, use append() and then reverse() to save time. You don't need to delete all array for each time.

  • Scroll trigger or willDisplay cell method loading

Let's start. You can create a child for your posts timestamp or date/time being global. To provide like Instagram seconds, weeks I advice you using UTC time. So I will call this: (timeUTC)

For sorting your all post, use since1970 timestamp. So I will call this (timestamp) and then also you can keep another node as (reversedTimestamp) adding - prefix to timestamp. So when you use queryOrdered to this node. You can handle latest 5 post using with yourQuery.queryLimited(toFirst: 5).

1.Get UTC date/time for timeUTC node in Swift 3:

        let date = Date()
        let formatter = DateFormatter()
        formatter.locale = Locale(identifier: "en_US_POSIX")
        formatter.dateFormat = "yyyy-MM-dd HH:mm:ss ZZZ"
        formatter.timeZone = TimeZone(abbreviation: "UTC")
        let utcTimeZoneStr = formatter.string(from: date)

+0000 means it's universal time, look at http://time.is/tr/UTC

2.Get since1970 timestamp to sort posts in Swift 3:

let timestamp = (Date().timeIntervalSince1970 as NSString).doubleValue
let reversedTimestamp = -1.0 * timestamp

Now, you can save them on your Firebase posts like this.

"posts" : {
    "-KHLOy5mOSq0SeB7GBXv" : {
      "timestamp": "1475858019.2306"
      "timeUTC" : "2012-02-04 12:11:56 +0000"
    },
    "-KHLrapS0wbjqPP5ZSUY" : {
      "timestamp": "1475858010.1245"
      "timeUTC" : "2014-02-04 12:11:56 +0000"
    },

I will retrieve five by five post, so I'm doing queryLimited(toFirst: 5) in viewDidLoad:

let yourQuery = ...queryOrdered(byChild: "reverseTimestamp")
                   .queryEnding(atValue: "\(self.pageOnTimestamp)", childKey: "reverseTimestamp")

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

        if snapshot.value is NSNull {

            print("There is no post.")

        }
        else {

            yourQuery.queryLimited(toFirst: 5).observeSingleEvent(of: .value, with: { (snapshot) in

                self.posts.removeAll(keepingCapacity: true)

                for (i, snap) in snapshot.children.enumerated() {

                    if let postAllDict = snapshot.value as? [String: AnyObject] {
                        if let postDict = postAllDict[(snap as AnyObject).key as String] as? [String: AnyObject] {

                            let post = Post(key: (snap as AnyObject).key as String, postDict: postDict)
                            self.posts.append(post)
                        }
                    }
                }

                completion(true)
            })
        }
    })

If user reached latest post, you can handle it with willDisplay method like below, then you can call loadMore function.

func tableView(_ tableView: UITableView, willDisplay cell: UITableViewCell, forRowAt indexPath: IndexPath) {

   if self.posts.count - 1 == indexPath.row {
      // call loadMore function.
   }
}

In loadMore() function you can handle latest post's timestamp, then start-end query as with that, so you can easily continue with next first 5 posts while appending before array.

这篇关于您如何正确地从Firebase按时间顺序排序数据的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持!

09-03 14:27