为通用 NSFetchRequest 方法传递参数

Posted

技术标签:

【中文标题】为通用 NSFetchRequest 方法传递参数【英文标题】:Pass parameters for generic NSFetchRequest method 【发布时间】:2020-09-24 15:43:10 【问题描述】:

我需要为项目中的许多视图创建一个通用方法,以将数据导出为 .csv。为此,我需要传递一个“实体”参数,以便为所有人重用此函数。

“Alumno”实体的示例代码如下:

func exportData(???) 
    
    let container: NSPersistentContainer? = (UIApplication.shared.delegate as? AppDelegate)?.persistentContainer
   
    //*
    var exportData: [Alumno] = []
    let exportRequest: NSFetchRequest<Alumno> = Alumno.fetchRequest()
    //*
    
    let context = container?.viewContext
    
    do 
        exportData = try context!.fetch(exportRequest)
     catch 
        print("Error: \(error)")
    
    ...

现在,我如何在方法定义中传递“实体”参数(标有???),以及“exportData”数组和“exportRequest”定义(标有*)应该是什么,以便重用它要从其他视图调用方法以导出其数据?

谢谢。

【问题讨论】:

【参考方案1】:

如果您希望它适用于您的任何实体,那么它不需要知道它正在使用哪个实体。它可以使用NSManagedObject,而忽略子类。

应该是这样的

func exportData(class name: String) -> Void 
    // ...

    var exportData: [NSManagedObject] = []
    let exportRequest: NSFetchRequest<NSManagedObject> = NSFetchRequest(entityName: name)

    // ...

名称就是获取请求所需的全部内容。您将获得一组托管对象。

【讨论】:

好的,就是这样,谢谢!但是,这样做我得到另一个错误。稍后在我的代码中,我需要在循环中使用这些对象来获取 .csv 值:for data in exportData。并且data.csv()data.data(using: .utf8, allowLossyConversion: false) 都抛出错误:'NSManagedObject' 类型的值没有成员'csv',并且不能分别根据成员'utf8' 推断上下文基础 我不知道为什么第一个有效(使用具体的子类)而第二个无效(使用超类 NSManagedObject)-> (dropover.cloud/0e9f2c) 这是因为csv() 不是NSManagedObject 的一部分。它在您的应用程序中的某个位置。如果您扩展 NSManagedObject 以包含该功能,那么它应该可以工作。如果您不能这样做,那么您需要编辑您的问题以包含有关您的数据模型的更多详细信息。 谢谢汤姆。这是正确的!虽然现在还有另一个问题。在下一条评论中继续。【参考方案2】:

继续 Tom 的建议,他是对的:我定义了三个 csv() 方法来为我的每个实体获取 csv 字符串。比如“校友”一:

extension Alumno 

func csv() -> String 
    let coalescedNombre = nombre ?? ""
    let coalescedEspecialidad = especialidadRelacionada?.nombre ?? ""
    let coalescedCurso = cursoRelacionado?.nivel ?? ""
    let coalescedTutor = tutorRelacionado?.nombre ?? ""
    let coalescedMovil = movil ?? ""
    let coalescedCorreo = correo ?? ""
    let formatter = DateFormatter()
    formatter.dateFormat = "d MMM y, E HH:mm"
    let coalescedNacimiento = formatter.string(from: nacimiento!)
    return "\(coalescedNombre), \(coalescedEspecialidad), \(coalescedCurso), \(coalescedTutor), \(coalescedMovil), \(coalescedCorreo), \(coalescedNacimiento)\r\n"

但现在的问题是:如何匹配这些合并后的值来为其对应实体填充 csv 文件?我的意思是:我可以为所有这些方法编写等效方法,但是,我如何定义它的值?这不起作用:

extension NSManagedObject 

func csv() -> String 

    var entity = NSManagedObject.entity
    
    if entity == Alumno 
        let coalescedNombre = nombre ?? ""
        let coalescedEspecialidad = especialidadRelacionada?.nombre ?? ""
        let coalescedCurso = cursoRelacionado?.nivel ?? ""
        let coalescedTutor = tutorRelacionado?.nombre ?? ""
        let coalescedMovil = movil ?? ""
        let coalescedCorreo = correo ?? ""
        let formatter = DateFormatter()
        formatter.dateFormat = "d MMM y, E HH:mm"
        let coalescedNacimiento = formatter.string(from: nacimiento!)
        return "\(coalescedNombre), \(coalescedEspecialidad), \(coalescedCurso), \(coalescedTutor), \(coalescedMovil), \(coalescedCorreo), \(coalescedNacimiento)\r\n"

    

   if entity == ... 


【讨论】:

以上是关于为通用 NSFetchRequest 方法传递参数的主要内容,如果未能解决你的问题,请参考以下文章

如何将类型应用于 NSFetchRequest 实例?

如何将类型应用于 NSFetchRequest 实例?

C#:在运行时获取类型参数以传递给通用方法[重复]

存储过程,将表名作为参数传递

无法使用类型为“(NSFetchRequest<NSFetchRequestResult>)”的参数列表调用“获取”

将实例化的 System.Type 作为通用方法的类型参数传递