【问题标题】:The Basics of Parse Blocks in SwiftSwift 中解析块的基础知识
【发布时间】:2015-07-13 03:02:46
【问题描述】:

我在理解块的具体工作原理方面遇到了一点问题。

for x in self.activerestaurantIDArray
{
let namelabel = x.0
self.activenameArray.append(namelabel)

let distancelabel = x.1
self.activedistanceArray.append(distancelabel)

let imageFile = x.2 
imageFile.getDataInBackgroundWithBlock({ (imageData: NSData?, error: NSError?) -> Void in

if error == nil {
let realimage = UIImage(data: imageData!)
self.activeimageArray.append(realimage!)                          
}

println(self.activenameArray)
println(self.activedistanceArray)
println(self.activeimageArray)

})                         
}

在上面的代码中,我将信息附加到元组中的一个数组(命名为:activerestaurantIDArray),以便获得名称、距离和图像的单独数组。至于图像,我只能从解析中检索 PFFile,因此我必须将文件转换为 UIImage。

但是,当我这样做时,只有当 println() 位于块 (imageFile.getDataInBackgroundWithBlock) 内时,activeImageArray 的附加才有效。

如果我在盒子外面的任何地方println(self.activeimageArray),数组将变成零。我不确定为什么会发生这种情况,或者我应该如何确保附加值超出 Block{}。任何帮助将不胜感激。

【问题讨论】:

    标签: arrays swift parse-platform closures objective-c-blocks


    【解决方案1】:

    闭包(也称为是,块)是可以稍后调用的代码片段,它们本质上是函数。

    你在imageFile.getDataInBackgroundWithBlock做的是下载数据,当数据被下载时,imageFile.getDataInBackgroundWithBlock会调用你的block,把刚刚下载的东西的内容传递给你。

    这样做是因为下载必须在单独的线程中进行。否则你的主线程将冻结,不仅会给用户带来烦恼,而且在 5 秒无响应后,操作系统会杀死你的应用程序。 getDataInBackgroundWithBlock 为下载操作生成一个不同的线程,然后它通过调用你的块让你知道。这使您可以在不“冻结”或“挂起”您的应用的情况下下载任何内容。

    所以imageData 在块外时为零,因为您试图在块完成下载操作之前使用它。您的代码永远不会比下载操作运行得慢,因此您必须使用该块来实现您想要在操作完成下载时使用的代码,在这种情况下,设置 imageData。

    编辑添加,这不是 Parse 独有的。几乎任何可以冻结 UI 的框架都会执行这些操作并使用块实现通知。仍然可以通过使用委托来获得通知,但是自从在 Objective-C 中引入块后,人们一直在远离这种模式。

    【讨论】:

    • 感谢您的快速回复。但我有个问题。如果我要使用数组中的数据,是否建议将所有这些任务写在块下?
    • 仅当数组依赖于块时。最终,这一切都取决于您要做什么。
    • 在这种特殊情况下,我想用我在这里收集的数组中的数据加载表格单元格。那么为了填充单元格,必须在块内调用该函数?
    • 将您的数组声明为属性。把它填在块里。然后调用 reloadData(),并连接你的逻辑以使用该数组作为表格内容。
    最近更新 更多