这一节,我们通过实际的代码,来了解如何读写上一节创建的带有关系的 ENTITY。
在 Core Data 中创建记录
为了演示这个过程,我们在项目中添加了一个 Relationships.swift。在这里,定义了一个叫做 buildSeriesEpisodeAndHistory 的函数。在这个函数的实现里,先来创建一个 Series 和两个 Episode 对象:
func buildSeriesEpisodeAndHistory() {
  let series = Series(context: managedContext)
  series.id = 1
  series.title = "Build Boxue App"
  series.summary = "Let's build boxue App from scratch."
  let episode1 = Episode(context: managedContext)
  episode1.id = 1
  episode1.seriesId = 1
  episode1.title = "Core data basic idea"
  episode1.summary = "Basic core data operations."
  let episode2 = Episode(context: managedContext)
  episode2.id = 2
  episode2.seriesId = 1
  episode2.title = "Core data relationship"
  episode2.summary = "Build core data relationships by code."
}
再创建两个 History 对象表示 episode1/2 的浏览记录:
func buildSeriesEpisodeAndHistory() {
  /// The same as before...
  let history1 = History(context: managedContext)
  history1.id = 1
  history1.episodeId = 1
  history1.progress = 110
  history1.updatedAt = Date()
  let history2 = History(context: managedContext)
  history2.id = 2
  history2.episodeId = 2
  history2.progress = 50
  history2.updatedAt = Date()
}
创建好这些代表 ENTITY 记录的对象之后,我们可以像这样设置它们之间的关系:
func buildSeriesEpisodeAndHistory() {
  /// The same as before...
  episode1.ofSeries = series
  episode2.ofSeries = series
  series.episodes = NSSet(array: [episode1, episode2])
  history1.ofEpisode = episode1
  episode1.history = history1
  history2.ofEpisode = episode2
  episode2.history = history2
  CoreDataManager.shared.saveContext(managedContext)
}
完成后,还是使用 saveContext() 方法,Series,Episode 以及 History 的值,以及它们之间的关系,就写入 core data 了。
在 Core Data 中读取记录
接下来,为了验证写入的结果,我们再从 core data 中把这些数据读出来。这里,我们用读取 Series 举例:
func fetchSeries() {
  let fetchRequest: NSFetchRequest<Series> = Series.fetchRequest()
  let series = try! managedContext.fetch(fetchRequest)
  series.forEach {
    print($0.title!)
    print($0.summary!)
    print($0.episodes!)
  }
}
可以看到,读取表达一对多关系的 episodes 和读取普通属性是一样的。执行一下,就可以在控制台看到类似下面这样的结果:

这样我们就通过 Series 记录读到了所有和它关联的视频。并且,在打印的 Episode 对象的信息里,我们也可以看到之前设置的 reverse 关系 ofSeries,也指回了视频所在的系列,这说明两个方向的 relationships 都是可用的。
至于 History 和 Episode 记录的读取,大家可以自己试试,方式和道理都是一样的,我们就不再重复了。
What's next?
说到这,希望你还记得,之前我们说过一个向 Core Data 保存数据的问题,就是每次重新编译执行都会向 core data 写入重复的数据。这是因为我们还没有向大家介绍过如何删除 core data 记录。现在,我们已经做了足够充分的铺垫,下一节,结合 Delete Rule 和带有关系的 ENTITY,我们和大家分享 core data 中删除记录的操作。
 参与视频讨论
                                                        参与视频讨论