保存 API 对 coreData 的响应,访问时仍然显示 nil

saving API response to coreData, still shows nil when accessing

  func getGenreKeys(complition: @escaping (_ genre : GenreListModel?) -> ())
    {
        let genreUrl = URL(string: "\(baseUrl)\(genreListUrl)\(apiKey)")!
        
        urlSessionManager(url: genreUrl,toUseDataType: GenreListModel.self) { json in
            
            //json will contain genreList Object , which can be used to get keys
            switch json
            {
            case .success(let genreListData) :
                complition(genreListData)
                CoreData.shared.saveGenreList(json: genreListData)
            case .failure(let error) :
                print(error)
            }
        }
        
    }

以上是api完成码

  func saveGenreList(json: GenreListModel){
        let context = persistentContainer.viewContext
        let genreList = GenreList(context: context)
        
        json.genres?.forEach({ Genres in
            genreList.name = Genres.name
            do{
                try context.save()
             
            }
            catch{
                print("error in saving")
            }
        })
    }

这是我在完成 api 提取后保存数据所做的。

   var coreGenre : GenreList?

    func tableView(_ tableView: UITableView, numberOfRowsInSection section: Int) -> Int {
        return coreGenre?.name?.count ?? 0
 

上面的代码是 VC 的一部分,它需要获取 coreGenre.name 来给出计数,但它是 nill

但是当我尝试通过创建核心数据实体 class 的变量从 viewController 访问时,它 returns nill

怎么了?

我的回答基于代码 there。在您分享该代码的 GitHub 帐户中。

第一期:

你有:

var genrelist : GenreListModel? {
    didSet{
        //after getting data a table needs to reload and ui elements needs to be used in main thread only
        DispatchQueue.main.async {
            self.tableView.reloadData()
            
        }
    }
}

var coreGenre : [GenreList]?

override func viewWillAppear(_ animated: Bool) {
    ...
    ApiManager.shared.getGenreKeys { genre in
        self.genrelist = genre
    }
}

func tableView(_ tableView: UITableView, numberOfRowsInSection section: Int) -> Int {
    return coreGenre?.count ?? 0
}

func tableView(_ tableView: UITableView, cellForRowAt indexPath: IndexPath) -> UITableViewCell {
    ...
    genrelist?.genres?[indexPath.row].id
    ...
    cell.genreLabel.text = genrelist?.genres?[indexPath.row].name
    ...
}

第一期:
coreGenre 从未设置! genreList 已设置,但未设置 coreGenre。所以不要指望它会是 nil!
的其他东西 你没有写 coreGenre = something
所以 tableView(_:numberOfRowsInSection:) 总是 return 0.

做出你的选择。 genreListcoreGenre:

ApiManager.shared.getGenreKeys { genreList in
        self.coreGenre = genreList.genres
}

&

var coreGenre: [GenreList] {
    didSet { DispatchQueue.main.async { self.tableView.reloadData() } }
}

并删除 var genreList

或者,删除 coreGenre.

这应该可以解决 UITableView,这就是您的问题具有误导性的地方:这里没有 CoreData。在 completiongetGenreKeys() 中,你 return 的值。 CoreData在方法中保存值,仅此而已。

是:

API -> Parse Value -> Save in CoreData
                   -> Completion        -> Reload TableView to Display

现在在您的 CoreData 堆栈中,您有一个方法 saveGenreList(json:)。假设它有效,您保存它但永远不会检索它。

您的代码中没有 NSFetchRequest。看看如何在CoreData中执行fetch。

别再想CoreData,想明白问题了:

let retrieveValueFromAPI = "I got it"
let savedValue = retrieveValueFromAPI // (1)
return retrieveValueFromAPI

在 (1) 中,您将收到来自 Xcode 的未使用变量警告。这是完全相同的问题。这里它是一个“RAM 值”而不是磁盘值,但这是相同的逻辑。你没有使用你保存的东西。

您需要继续工作和调试。调试不仅可以解决问题。有几个步骤:

  • 重现问题
  • 找到它的 origin/understand 可能是什么问题
  • 解决问题

寻找它的起源,以及为什么,是你错过的步骤,要么是由于误解,要么是你的代码中没有足够的逐步研究。