无法将 String 类型的值转换为预期的参数类型 NSManagedObject
Cannot convert value of type String to expected argument type NSManagedObject
我正在做一个 Core Data 项目,我在从 TableViewController
:
中删除项目时遇到编译器错误
无法将字符串类型的值转换为预期的参数类型 NSManagedObject
代码如下:
var listArr:[String] = []
override func viewDidLoad() {
super.viewDidLoad()
let appDelegate = UIApplication.shared.delegate as! AppDelegate
let context = appDelegate.persistentContainer.viewContext
let request = NSFetchRequest<NSFetchRequestResult>(entityName:"Entity")
request.returnsObjectsAsFaults = false
do {
let results = try context.fetch(request)
if results.count > 0 {
for result in results as! [NSManagedObject] {
if let listName = result.value(forKey: "listName") {
listArr.append(listName as! String)
}
}
}
} catch {
// Handle error
print(error)
}
}
override func tableView(_ tableView: UITableView, cellForRowAt indexPath: IndexPath) -> UITableViewCell {
let identifier = "cellID"
let cell = tableView.dequeueReusableCell(withIdentifier: identifier, for: indexPath)
// Configure the cell...
cell.textLabel?.text = listArr[indexPath.row]
return cell
}
// Override to support editing the table view.
override func tableView(_ tableView: UITableView, commit editingStyle: UITableViewCellEditingStyle, forRowAt indexPath: IndexPath) {
if editingStyle == .delete {
// Delete the row from the data source
let appDelegate = UIApplication.shared.delegate as! AppDelegate
let context = appDelegate.persistentContainer.viewContext
context.delete(listArr[indexPath.row]) //The error is here
listArr.remove(at: indexPath.row)
}
self.tableView.reloadData()
}
我需要更改什么?
您可以通过两种方式从 core-data 填充 table。您可以使用 NSFetchedResultsController
来跟踪核心数据的变化并保持数据同步。或者您可以进行一次提取并将要显示的值存储在我们自己的数据源(例如数组)中。
使用 NSFetchedResultsController
,您将在数据更改时获得更新。使用此模型,删除行的正确方法是从 core-data 中删除它并等待 NSFetchedResultsController
的回调来更新您的视图。
单次获取(正如您所做的那样)您不会在 core-data 更改时获得更新。在此模型中,您可以简单地从数组中删除对象并更新视图。更新 core-data 是另一项与您的视图或数据源无关的任务。在这种情况下,您应该使用 persistentContainer
performBackgroundTask
来获取要删除的对象,然后在后台将其删除。为此,您需要有一种方法来获取要删除的托管对象。我不知道您存储的是哪种字符串 - 但如果它们是唯一的,您可以将它们用于您的提取。否则,您还必须存储对象的一些唯一 ID,例如它的 objectID。
您正在调用的 delete()
方法将 NSManagedObject
作为其唯一参数。您正在从 listArr
数组中传递一个元素,该数组是一个字符串数组。
说起来好像很明显,但是如果你想删除一个托管对象,你需要告诉Core Data删除哪一个。它不知道如何处理字符串。
我猜测(因为你没说)你的listArr
是由存储在核心数据中的字符串组成的属性 一个实体。您正在某处获取数据并仅保存字符串。没关系 只要您的数据存储是 read-only,至少在应用程序的这一部分是这样。您可以显示字符串,但无法返回并更新核心数据,因为您没有必要的信息。
如果这是真的,那么您应该使用托管对象数组而不是字符串数组。当您需要字符串值时,从托管对象之一获取它。当您需要删除条目时,请删除该托管对象。
我正在做一个 Core Data 项目,我在从 TableViewController
:
无法将字符串类型的值转换为预期的参数类型 NSManagedObject
代码如下:
var listArr:[String] = []
override func viewDidLoad() {
super.viewDidLoad()
let appDelegate = UIApplication.shared.delegate as! AppDelegate
let context = appDelegate.persistentContainer.viewContext
let request = NSFetchRequest<NSFetchRequestResult>(entityName:"Entity")
request.returnsObjectsAsFaults = false
do {
let results = try context.fetch(request)
if results.count > 0 {
for result in results as! [NSManagedObject] {
if let listName = result.value(forKey: "listName") {
listArr.append(listName as! String)
}
}
}
} catch {
// Handle error
print(error)
}
}
override func tableView(_ tableView: UITableView, cellForRowAt indexPath: IndexPath) -> UITableViewCell {
let identifier = "cellID"
let cell = tableView.dequeueReusableCell(withIdentifier: identifier, for: indexPath)
// Configure the cell...
cell.textLabel?.text = listArr[indexPath.row]
return cell
}
// Override to support editing the table view.
override func tableView(_ tableView: UITableView, commit editingStyle: UITableViewCellEditingStyle, forRowAt indexPath: IndexPath) {
if editingStyle == .delete {
// Delete the row from the data source
let appDelegate = UIApplication.shared.delegate as! AppDelegate
let context = appDelegate.persistentContainer.viewContext
context.delete(listArr[indexPath.row]) //The error is here
listArr.remove(at: indexPath.row)
}
self.tableView.reloadData()
}
我需要更改什么?
您可以通过两种方式从 core-data 填充 table。您可以使用 NSFetchedResultsController
来跟踪核心数据的变化并保持数据同步。或者您可以进行一次提取并将要显示的值存储在我们自己的数据源(例如数组)中。
使用 NSFetchedResultsController
,您将在数据更改时获得更新。使用此模型,删除行的正确方法是从 core-data 中删除它并等待 NSFetchedResultsController
的回调来更新您的视图。
单次获取(正如您所做的那样)您不会在 core-data 更改时获得更新。在此模型中,您可以简单地从数组中删除对象并更新视图。更新 core-data 是另一项与您的视图或数据源无关的任务。在这种情况下,您应该使用 persistentContainer
performBackgroundTask
来获取要删除的对象,然后在后台将其删除。为此,您需要有一种方法来获取要删除的托管对象。我不知道您存储的是哪种字符串 - 但如果它们是唯一的,您可以将它们用于您的提取。否则,您还必须存储对象的一些唯一 ID,例如它的 objectID。
您正在调用的 delete()
方法将 NSManagedObject
作为其唯一参数。您正在从 listArr
数组中传递一个元素,该数组是一个字符串数组。
说起来好像很明显,但是如果你想删除一个托管对象,你需要告诉Core Data删除哪一个。它不知道如何处理字符串。
我猜测(因为你没说)你的listArr
是由存储在核心数据中的字符串组成的属性 一个实体。您正在某处获取数据并仅保存字符串。没关系 只要您的数据存储是 read-only,至少在应用程序的这一部分是这样。您可以显示字符串,但无法返回并更新核心数据,因为您没有必要的信息。
如果这是真的,那么您应该使用托管对象数组而不是字符串数组。当您需要字符串值时,从托管对象之一获取它。当您需要删除条目时,请删除该托管对象。