为我的漫画收藏开发一个小应用程序遇到了这个问题:
在我的第二个"添加漫画" VC我有一个按钮和下面的函数,但我在manged上下文中保存了TWICE实体(至少,我认为这是问题)
例如,如果我在主VC表视图中显示了2个漫画,请转到"添加漫画VC"然后保存第三个,返回主VC我将打印3个带有标题,数字等的对象,但也会打印2个没有数据的新对象,因为我已经保存了两次马槽上下文a"右边一个&#34 ;另一个具有相同数量的对象但是空的。如果我继续添加第4部漫画,我将获得6部完整漫画+第4部以及更多6部"空白主题"默认值"没有标题"
let kComicEntityName = "Comic"
func addingSingleComic(gotTitle: String, gotIssue: Int16, gotInCollection: Bool ) {
guard let appDelegate = UIApplication.shared.delegate as? AppDelegate else {return}
let managedContext = appDelegate.persistentContainer.viewContext
let entity = NSEntityDescription.entity(forEntityName: kComicEntityName, in: managedContext)!
let comicToAdd = Comic(entity: entity, insertInto: managedContext)
comicToAdd.comicTitle = gotTitle
comicToAdd.issueNumber = gotIssue
comicToAdd.inCollection = gotInCollection
do {
try managedContext.save()
} catch let error as NSError {
print("could not save. \(error), \(error.userInfo)")
}
print("new single comic crated: title: \(comicToAdd.comicTitle ?? "!! not title !!"), n. \(comicToAdd.issueNumber), owned?: \(comicToAdd.inCollection)")
}
主VC中的我用它来检查核心数据中的项目
func asyncPrintEntities() {
self.asyncComicEntityArray.removeAll(keepingCapacity: true)
guard let appDelegate = UIApplication.shared.delegate as? AppDelegate else {return}
let managedContext = appDelegate.persistentContainer.viewContext
let comicFetch : NSFetchRequest<Comic> = Comic.fetchRequest()
asyncFetchRequest = NSAsynchronousFetchRequest<Comic>(fetchRequest: comicFetch) {
[unowned self] (result: NSAsynchronousFetchResult) in
guard let AllComicEntityResult = result.finalResult else {
return
}
self.asyncComicEntityArray = AllComicEntityResult
//************************************
do {
self.asyncComicEntityArray = try managedContext.fetch(comicFetch)
if self.asyncComicEntityArray.count > 0 {
print("Ok! model is not empty!")
} else {
print("No entites availabe")
}
} catch let error as NSError {
print("Fetch error: \(error) description: \(error.userInfo)")
}
guard self.asyncComicEntityArray != nil else {return}
for comicFoundInArray in self.asyncComicEntityArray {
let entity = NSEntityDescription.entity(forEntityName: self.kComicEntityName, in: managedContext)!
var comicTouse = Comic(entity: entity, insertInto: managedContext)
// var comicTouse = Comic() //to be deleted since this kind of init is not allowed, better above insertInto
comicTouse = comicFoundInArray as! Comic
print("comic title: \(comicTouse.comicTitle ?? "error title"), is it in collection? : \(comicTouse.inCollection)")
}
self.MyTableView.reloadData()
//************************************
}
// MARK: - async fetch request 3
do {
try managedContext.execute(asyncFetchRequest)
} catch let error as NSError {
print("Could not fetch \(error), \(error.userInfo)")
}
//end of function
}
答案 0 :(得分:0)
在addingSingleComic
{}创建一个新的Comic
:
let comicToAdd = Comic(entity: entity, insertInto: managedContext)
然后将值赋给对象的属性。
另外,在asyncPrintEntities
中,您还可以在此处创建新的Comic
个对象:
var comicTouse = Comic(entity: entity, insertInto: managedContext)
这次不为对象的属性赋值。他们没有标题等,因为你创建了它们但从未分配过标题。此行对asyncComicEntityArray
中的每个对象执行一次,因此如果数组有两个对象,则创建两个不包含数据的新对象。除了comicToUse
之外,您不能在任何地方使用print
,但它仍然存在于托管对象上下文中,并且在您下次保存更改时仍会保存。
这就是为什么你要获得额外的条目 - 因为你是在这行代码中创建它们的。目前尚不清楚为什么要在这里创建它们。您刚刚执行了一个获取请求,然后您立即创建了一堆您没有使用的无数据条目。看起来整个for
循环可能只是被删除,因为它唯一能做的就是创建这些额外的条目。