我想要將從遠程文件下載的一些數據存儲在CoreData中。他的數據可能以前已經下載過,然後需要將更改添加到核心數據。 我使用這裏顯示的代碼。在三個地方我使用Fetchrequest來檢查數據是否已經存在於數據庫中。我對請求使用謂詞。在代碼中,我添加了評論來區分它們。如果該項目已經在coreData中,我更新數據,否則我會實例化一個新項目。將該項目添加到核心數據的代碼位於該類的便利init中。這工作正常。我得到的問題是這樣的: 這個代碼中的第一次id等於0,所以schoolFetch被執行。添加謂詞nr 1不會導致錯誤,並且學校類的實例化將其id設置爲0. 第二次id = 1。這意味着位置是學校的一部分的locationItem被檢查並實例化。爲了將位置添加到學校,執行fetchrequest以獲得schoolInstance。使用謂詞2。儘管之前添加的schoolInstance沒有被檢索,但這不會產生錯誤,但是如果謂詞沒有被使用(註釋掉)。 檢索schoolInstance之後,我使用fetchrequest來檢查位置是否已經在coredata中。如果沒有,它被實例化,否則其數據被更新。謂詞nr 3給出了一個運行時錯誤,除了EXC_BAD_ACCESS(代碼= 1,地址= 0x1)外其他都沒有說明。在調試器窗口中沒有給出錯誤描述。 所以我有兩個問題: a)謂詞nr 2爲什麼不返回先前插入的項目? b)爲什麼謂詞nr 3給出錯誤?瞭解快速添加謂詞到NSFetchrequest
我以這種方式組織這段代碼,因爲它有可能首先接收有關學校信息的位置信息。
if id == 0 {
//get school
let schoolFetch = NSFetchRequest<StreekgidsSchool>(entityName: "School")
schoolFetch.predicate = NSPredicate(format: "locationId == %@", id) // predicate 1
do {
let fetchedSchool = try streekgidsModel?.context.fetch(schoolFetch)
if let school = fetchedSchool?.first{
school.name = name
school.locationId = id
school.colorValue = color
schoolInstance = school
}
else {
//create new entry in coredata for school
schoolInstance = StreekgidsSchool(name: name, context: (streekgidsModel?.context)!)
schoolInstance?.locationId = id
schoolInstance?.colorValue = color
}
} catch {
fatalError("Failed to fetch Schooldata: \(error)")
}
}
else {
//check if school already is defined
let schoolFetch = NSFetchRequest<StreekgidsSchool>(entityName: "School")
schoolFetch.predicate = NSPredicate(format: "locationId == %@", 0) //predicate 2
do {
let fetchedSchool = try streekgidsModel?.context.fetch(schoolFetch)
if let school = fetchedSchool?.first{
schoolInstance = school
}
else {
//create new entry in coredata for school
schoolInstance = StreekgidsSchool(id: 0, context: (streekgidsModel?.context)!)
}
} catch {
fatalError("Failed to fetch Schooldata: \(error)")
}
//get location
let locationFetch = NSFetchRequest<StreekgidsLocation>(entityName: "Location")
locationFetch.predicate = NSPredicate(format: "locationId == %@", id) //predicate 3
do {
let fetchedLocation = try streekgidsModel?.context.fetch(locationFetch)
if let location = fetchedLocation?.first{
location.name = name
location.locationId = id
location.colorValue = color
location.school = schoolInstance
}
else {
//create new entry in coredata for location
let locationInstance = StreekgidsLocation(name: name, context: (streekgidsModel?.context)!)
locationInstance.locationId = id
locationInstance.colorValue = color
}
} catch {
fatalError("Failed to fetch Schooldata: \(error)")
}
}
是不是%@通常用於表示謂詞中的對象或字符串?現在不能輕易檢查,但我會檢查什麼會更好地匹配你的id作爲一個Int。可能%i或%d – Magnas
該文檔指出以下內容:「%@是一個對象值的var arg替換 - 通常是字符串,數字或日期」。此外,所有三個謂詞的格式都是相同的,但只有第三個謂詞會導致錯誤 – KvdLingen
或者可能:let predicate = NSPredicate(format:「id ==%@」,id as NSNumber) – Magnas