Ios 在CellForRowatineXpath中使用PFQuery

Ios 在CellForRowatineXpath中使用PFQuery,ios,swift,uitableview,parse-platform,pfquery,Ios,Swift,Uitableview,Parse Platform,Pfquery,我在考虑PFQuery 我正在开发一个向用户显示提要的应用程序,它还为每个帖子显示一个类似计数器(如Facebook应用程序或Instagram应用程序) 因此,在我的PFQueryTableViewController中,我有我的主查询,它基本上显示了所有帖子: override func queryForTable() -> PFQuery { let query = PFQuery(className: "Noticias") query.orderByDescend

我在考虑
PFQuery

我正在开发一个向用户显示提要的应用程序,它还为每个帖子显示一个类似计数器(如Facebook应用程序或Instagram应用程序)

因此,在我的
PFQueryTableViewController
中,我有我的主查询,它基本上显示了所有帖子:

override func queryForTable() -> PFQuery {
    let query = PFQuery(className: "Noticias")
    query.orderByDescending("createdAt")   
    return query
}
我使用另一个查询来计算另一个类中的喜欢数,解析该类包含所有喜欢

override func tableView(tableView: UITableView, cellForRowAtIndexPath indexPath: NSIndexPath, object: PFObject?) -> PFTableViewCell? {
    var cell = tableView.dequeueReusableCellWithIdentifier("FeedCellIdentifier") as! FeedCell!
    if cell == nil {
        cell = FeedCell(style: UITableViewCellStyle.Default, reuseIdentifier: "FeedCellIdentifier")
    }

    let query2 = PFQuery(className:"commentsTable")
    query2.whereKey("newsColumn", equalTo: object!)
    query2.findObjectsInBackgroundWithBlock {
        (objectus: [PFObject]?, error: NSError?) -> Void in

        if error == nil {

            let quantidade = objectus!.count

            let commentQuantidade = String(quantidade)

            cell.comentariosLabel.text = commentQuantidade
        } else {
            // Log details of the failure
            print("Error: \(error!) \(error!.userInfo)")
        }
    }
这种编码方式有效,我实现了我想要的,但是!我知道我在重用单元格,我知道每当单元格出现时,这段代码都会被调用

我知道这些事实:

  • 每次我滚动tableview时,都会向Parse Cloud发送大量查询请求

  • 例如,当我滚动tableview时,可能会看到值发生变化,因为我在重用单元格。一篇文章的值是我以前的单元格,然后通过新的查询刷新它。这样做很有效,但不利于用户体验

  • 所以,我的主要疑问是,这是正确的编码方式吗?我不这么认为,我只是想要另一种观点或想法

    谢谢

    编辑1

    正如我所说,我已经将count方法更新为
    countobjectsinbackgroundithblock
    ,而不是
    findobjectsinbackgroundithblock
    ,但我无法将查询移动到ViewDidLoad,因为我使用
    对象
    来检查每篇文章的评论数

    编辑2 我嵌入了查询以计算每篇文章的评论数并打印结果,现在我认为我的代码比以前的版本更好,但我无法将结果传递给标签,因为我收到一个错误:

    使用未解析的标识符“commentCount”

    我正在阅读一些关于
    Struct

    下面是我更新的代码:

    import UIKit
    import Social
    
    class Functions: PFQueryTableViewController, UISearchBarDelegate {
    
    override func shouldAutorotate() -> Bool {
        return false
    }
    
    var passaValor = Int()
    let swiftColor = UIColor(red: 13, green: 153, blue: 252)
    struct PostObject{
        let post : PFObject
        let commentCount : Int
    }
    
    var posts : [PostObject] = []
    
    
    // Initialise the PFQueryTable tableview
    override init(style: UITableViewStyle, className: String!) {
        super.init(style: style, className: className)
    }
    
    required init(coder aDecoder: NSCoder) {
        super.init(coder: aDecoder)!
        // The className to query on
        self.parseClassName = "Noticias"
    
        // The key of the PFObject to display in the label of the default cell style
        self.textKey = "text"
    
        // Uncomment the following line to specify the key of a PFFile on the PFObject to display in the imageView of the default cell style
        self.imageKey = "image"
    
        // Whether the built-in pull-to-refresh is enabled
        self.pullToRefreshEnabled = true
    
        // Whether the built-in pagination is enabled
        self.paginationEnabled = true
    
        // The number of objects to show per page
        self.objectsPerPage = 25
    }
    
    // Define the query that will provide the data for the table view
    
    override func queryForTable() -> PFQuery {
        let query = super.queryForTable()
    
        return query
    }
    
    
    
    override func viewWillAppear(animated: Bool) {
        super.viewWillAppear(true)
        loadObjects()
    }
    
    // In a storyboard-based application, you will often want to do a little preparation before navigation
    override func viewDidLoad() {
        super.viewDidLoad()
        // navigationBarItems()
    
    
        let query = PFQuery(className:"Noticias")
        query.findObjectsInBackgroundWithBlock {
            (objects: [PFObject]?, error: NSError?) -> Void in
    
            // The find succeeded.
            print("Successfully retrieved \(objects!.count) scores.")
            // Do something with the found objects
            if let objects = objects {
                for object in objects {
                    let queryCount = PFQuery(className:"commentsTable")
                    queryCount.whereKey("newsColumn", equalTo: object)
                    queryCount.countObjectsInBackgroundWithBlock {
                        (contagem: Int32, error: NSError?) -> Void in
                        let post = PostObject(object, commentCount:commentCount)
                        posts.append(post)
                        print("Post \(object.objectId!) has \(contagem) comments")
                    }
                    self.tableView.reloadData()
                }
            }
        }
    
        //Self Sizing Cells
        tableView.estimatedRowHeight = 350.0
        tableView.rowHeight = UITableViewAutomaticDimension
    
    
    }
    
    
    
    // Define the query that will provide the data for the table view
    
    //override func tableView(tableView: UITableView, cellForRowAtIndexPath indexPath: NSIndexPath) -> UITableViewCell
    override func tableView(tableView: UITableView, cellForRowAtIndexPath indexPath: NSIndexPath, object: PFObject?) -> PFTableViewCell? {
    var cell = tableView.dequeueReusableCellWithIdentifier("FeedCellIdentifier") as! FeedCell!
    if cell == nil {
        cell = FeedCell(style: UITableViewCellStyle.Default, reuseIdentifier: "FeedCellIdentifier")
    }
    
    cell?.parseObject = object
    
    if let assuntoNoticia = object?["assunto"] as? String {
        cell?.assuntoNoticia?.text = assuntoNoticia
    }
    
    
    if let pontos = object?["pontos"] as? Int {
        let pontosPosts = String(pontos)
        cell?.pontosLabel?.text = String(pontosPosts)
    }
    
    
    if let zonaLabel = object?["zona"] as? String {
        cell?.zonaLabel?.text = zonaLabel
    }
    
    
    if let criticidade = object?["criticidade"] as? String {
        if criticidade == "Problema"{
    
            cell.criticidadeNoticia.backgroundColor = UIColor.redColor()
        } else {
            cell.criticidadeNoticia.backgroundColor = UIColor.greenColor()
        }
    }
    
    return cell
    }
    }
    
    打印结果:

    成功检索到5个分数

    Post wSCsTv8OnH有4条评论

    发布LbwBfjWPod有0条评论

    帖子fN4ISVwqpz有0条评论

    帖子1rXdQr2A1F有1条评论

    Post eXogPeTfNu有0条评论


    在将信息显示在tableview中之前,您应该先进行查询。

    更好的做法是在加载视图时查询所有数据并将其保存到模型中,然后在“table view scroll”中从中读取数据。处理查询时,您可以显示正在下载的指示符或占位符数据。查询完成后,您将调用
    tableView.reloadData()

    您可以通过如下方式创建新变量来完成此操作:

     var cellModels : [PFObject] = []
    
    struct PostObject{
     let post : PFObject
     let commentCount : Int
    }
    
    var posts : [PostObject] = []
    
    查询2中。findObjectsInBackgroundWithBlock

     for object in objectus{
       self.cellModels.append(object)
     }
     self.tableView.reloadData()
    
    并在
    单元格中按行索引路径

    let model = cellModels[indexPath.row]
    // configure cell according to model
    // something like cell.textLabel.text = model.text
    
    let post = posts[indexPath.row]
    cell.postCountLabel.text = String(post.commentCount)
    // configure cell accordingly
    
    p.S如果您只需要获取对象的计数,您应该查看方法
    countObjectsInBackgroundWithBlock
    。因为如果有很多注释,例如
    findObjectsInBackgroundWithBlock
    将返回最多1000个对象,并且您仍然不会下载整个对象,只有一个数字,这将加快查询速度并节省用户的移动计划

    更新:如果需要存储大量注释,也可以创建简单的
    结构
    ,如下所示:

     var cellModels : [PFObject] = []
    
    struct PostObject{
     let post : PFObject
     let commentCount : Int
    }
    
    var posts : [PostObject] = []
    
    当您查询您的帖子时,您将循环接收到的对象并填充
    posts
    array

    for object in objects{
      // create countObjectsInBackgroundWithBlock query to get comments count for object
      // and in result block create
      let post = PostObject(object, commentCount:commentCount)
      posts.append(post)
    
    } 
    tableView.reloadData()
    
    并在
    单元格中按行索引路径

    let model = cellModels[indexPath.row]
    // configure cell according to model
    // something like cell.textLabel.text = model.text
    
    let post = posts[indexPath.row]
    cell.postCountLabel.text = String(post.commentCount)
    // configure cell accordingly
    

    回答得很好,我正在尝试在我的代码中应用您所解释的内容,我将发布一个更新。我已经阅读了文档并改进了我的方法,将
    countobjectsinbackgroundithblock
    改为
    findobjectsinbackgroundithblock
    ,现在当我将查询移动到viewDidLoad时,我无法引用对象
    query2.whereKey(“newsColumn”,equalTo:object!)
    对象是什么类型的
    object
    ?您在哪里分配它?是的,它看起来比开始时好多了。您应该将
    (contagage:Int32,error:NSError?)替换为
    (contagage:Int32,error:NSError?->Void in let post=PostObject(object,commentCount:commentCount)
    (contagage:Int32,error:NSError?)->Void in let post=PostObject(object,commentCount:contagage)
    请报告您的进度,我是来帮助您的。您的
    numberofrowsinssection
    方法是什么?我会将
    返回帖子。count
    放在那里。