【问题标题】:Use Realm with Collection View Data Source Best Practise将 Realm 与集合视图数据源一起使用最佳实践
【发布时间】:2016-03-18 02:08:57
【问题描述】:

我会尽量简短。

我有一个 API 请求,我从中获取数据(即 Parse)。

当我得到结果时,我会将其写入 Realm,然后将它们添加到 UICollectionView 的数据源中。

有些请求需要更多时间,它们是异步运行的。在重新加载数据源和集合视图后,我得到了所需的结果。

我正在将结果中所需的更新写入我的 Realm 数据库。

我读到可以使用 Realm 的Results。但老实说,我不明白。我想有一种动态且安全的方式来处理集合视图和领域。这是我现在的方法。

这就是我目前填充集合视图的数据源的方式:

声明

var dataSource = [Realm_item]()

其中Realm_item 是一个领域Object 类型。

循环和写入

override func viewDidLoad() {
    super.viewDidLoad()
    for nowResult in FetchedResultsFromAPI
    {
        let item = Realm_item()
        item.item_Title = nowResult["Title"] as! String
        item.item_Price = nowResult["Price"] as! String
        // Example - Will write it later after the collectionView Done - Async request
        GetFileFromImageAndThanWriteRealm(x.image) 
        // Example - Will write it later after the collectionView Done - Async request
        dataSource.append(item)
    }

   //After finish running over the results *Before writing the image data*
    try! self.realm.write {
        self.realm.add(self.dataSource)
    }
    myCollectionView.reloadData()
}

在我将图像写入 Realm 到一个已经创建的“对象”之后。相同的 Realm Object(具有相同的主键)会在数据源中自动更新吗?

在我将更新写入 Realm DB 中的同一对象后,从数据源更新对象的正确方法是什么?

更新

模型类

class Realm_item: Object {
   dynamic var item_ID : String!
    dynamic var item_Title : String!
    dynamic var item_Price : String!
    dynamic var imgPath : String?

    override class func primaryKey() -> String {
        return "item_ID"
    }
}

首先,我正在检查 Realm 中是否存在“object id”。如果是,我从 Realm 获取对象并将其附加到数据源。如果它不存在,我会创建一个新的 Realm 对象,将其写入并添加它。

从 Parse 中获取数据

这发生在viewDidLoad 方法中并准备数据源:

var query = PFQuery(className:"Realm_item")
query.limit = 100
query.findObjectsInBackgroundWithBlock { (respond, error) -> Void in
    if error == nil
    {
        for x in respond!
        {            
            if let FetchedItem =  self.realm.objectForPrimaryKey(Realm_item.self,  key: x.objectId!)
            {
                self.dataSource.append(FetchedItem)        
            }
            else
            {
                let item = Realm_item()
                item.item_ID = x.objectId
                item.item_Title = x["Title"] as! String
                item.item_Price = x["Price"] as! String
                let file = x["Images"] as! PFFile
                RealmHelper().getAndSaveImageFromPFFile(file, named: x.objectId!)
                self.dataSource.append(item)
            }
        }

        try! self.realm.write {
            self.realm.add(self.dataSource)
        }

        self.myCollectionView.reloadData()
        print(respond?.count)
    }
}

谢谢!

【问题讨论】:

    标签: ios swift uicollectionview realm


    【解决方案1】:

    您在这里似乎有一些疑问和问题,所以我会尽力而为。

    我建议您使用 Results 类型作为数据源,例如:

    var dataSource: Results<Realm_item>?

    那么,在你的viewDidLoad()

    dataSource = realm.objects(Realm_item).

    在使用dataSource之前一定要使用相关的错误检查。我们使用可选的Results<Realm_item>,因为您使用它的领域对象需要首先初始化。即,如果您尝试声明类似 let dataSource = realm.objects(Realm_item) 的结果,您将得到类似 "Instance member * cannot be used on type *" 的信息。


    Realm documentation(当您像我一样将 Realm 作为初学者使用 Realm 时,这是一个写得很好的和有用的参考资料),它对结果有这样的说法......

    结果是实时的、自动更新基础数据的视图,这意味着无需重新获取结果。修改影响查询的对象将立即反映在结果中。

    您的里程可能会有所不同,具体取决于您如何设置所有内容。您可以尝试发布您的 Realm 模型和 Parse 相关代码以供审查和评论。

    你的最后一个问题:

    在我将更新写入 Realm DB 中的同一对象后,从数据源更新“对象”的正确方法是什么?

    我想您是在询问更新基础数据时更新 UI (CollectionView) 的最佳方式?如果是这样……

    您可以订阅 Realm notifications 以了解 Realm 数据何时更新,例如指示您应用的 UI 何时应该刷新,而无需重新获取您的结果。

    【讨论】:

    • 首先,谢谢!我将更新我上面的代码以提供有关它的更多信息。
    • 我已经更新了代码:)。几个问题 - 1)对于“结果”类型的数组,我也可以设置特定的查询吗?例如,就像我在上面所做的那样?通过附加对象而不只是通过查询来创建“结果”数组? 2)如果我注册到 Realm 通知,我如何更新数据源中的特定项目?谢谢!
    猜你喜欢
    • 2015-05-13
    • 1970-01-01
    • 1970-01-01
    • 2011-06-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2011-03-06
    • 2018-07-07
    相关资源
    最近更新 更多