【问题标题】:How to cast T.Type for an NSFetchRequest?如何为 NSFetchRequest 转换 T.Type?
【发布时间】:2019-04-10 18:22:48
【问题描述】:

我有一个方法签名:func fetch<T>(_ model: T.Type, predicate: NSPredicate?, sorted: Sorted?, completion: (([T]) -> Void)) where T: Storable,我想在 NSFetchRequest 中使用model

在这种情况下,使用extension NSManagedObject: Storable {},并且Storable协议内部有一些基本的CRUD方法定义。

我试过了:

  • T 转换为NSManagedObject,但这会导致运算符优先级错误。因此,(T as! NSManagedObject) 不起作用。

  • 只使用NSFetchRequest<T>(),但编译器告诉我T does not conform to NSFetchRequestResult

  • where T: Storable, NSManagedObject 但这意味着必须更新我的协议以获得实现细节,我不想去那里。

  • (model as! NSManagedObject).fetchRequest()Cast from 'T.Type' to unrelated type 'NSManagedObject' always fails

我想要实现的基本上是:如果可能的话,我希望能够fetch(User.self, ...) 使用该方法的当前签名。

【问题讨论】:

  • 我建议使用协议扩展,例如this
  • @vadian 有趣,我会使用我自己的Storable 协议而不是 Fetchable 进行扩展,对吧?
  • @vadian 你的链接答案中的 associatedtype 不是以这种方式与NSManagedObject 紧密耦合吗?
  • 这只是一个如何使用带有关联类型的协议扩展的示例。是的,关联类型始终是NSManagedObject 子类。使已经泛型的类型像 NSFetchRequest more 泛型 是完全不可能的
  • 我偶然发现了一种方法来做到这一点,所以我回答了我自己的问题,但非常感谢你的帮助,@vadian!

标签: swift generics core-data


【解决方案1】:

答案是将T.Type 转换为NSManagedObject.Type 以获得类型,然后调用.fetchRequest()

func fetch<T: Storable>(_ model: T.Type, predicate: NSPredicate?, sorted: Sorted?, completion: (([T]) -> Void)) {
    guard let managedObjectType = model as? NSManagedObject.Type else {
        return
    }

    let fetchRequest = managedObjectType.fetchRequest()
    fetchRequest.predicate = predicate
    ...
}

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 2019-09-06
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2020-08-20
    • 1970-01-01
    • 2021-02-26
    • 2017-03-21
    相关资源
    最近更新 更多