如何正确使用 Swift 中的泛型将不同类型的对象存储在 Realm 的列表中?

How to properly use generics in Swift to store different types of objects in a list in Realm?

我遇到 Realm 抛出错误的问题,指出我的类型 'Category' 不受 Realm 管理。

对于上下文,'Category' 可以包含 'Mistakes' 或 'Subjects' 类型的集合。 'Subject' 还可以包含 'Category' 的集合,其中包含 'Mistake' 的集合。因此,我正在使用泛型,这样我就不必创建两个单独的数据模型来对这两个数据模型进行分组。

class Category<O:Object>:Object{

//properties
@objc dynamic var categoryName:String = ""

//relationships
let ChildObjects = List<O>() //type of child object is to be set by the generic type; two possible types: subjects & mistakes

//mother objects
var Subjects = LinkingObjects(fromType: Subject.self, property: "MistakeCategories") //For Mistake Categories

}

我使用以下代码加载一类科目的结果:

var CategoryDatabase:Results<Category<Subject>>!

CategoryDatabase = R.objects(Category<Subject>.self)

我也试过使用下面的代码:

var CategoryDatabase:Results<Category<Subject>>!

CategoryDatabase = R.objects(Category.self)

尽管如此,我还是遇到了以下错误。

*** Terminating app due to uncaught exception 'RLMException', reason: 'Object type '_TtGC8Go_For_A8CategoryCSo16RealmSwiftObject_' not managed by the Realm'

我试图在互联网上搜索可能的解决方案,但他们的问题与我的问题并不完全相同。尽管如此,我发现 this 这可能是我收到错误的原因的可能答案。但是,错误及其原因不同。

这是我的通用函数,在将不同类型的对象存储到 Realm 数据库时可以正常工作:

let realm = try! Realm()

func createObject<T: Object>(_ object: T) {
     do {
         try realm.write {
             realm.add(object)
           }
        } catch {
             print(error)
           }
        }

这行不通

let ChildObjects = List<O>() //...two possible types: subjects & mistakes

Realm Collections(Result,List)是同构的,只能存储一种对象类型的零个或多个实例;例如您不能在同一列表对象中存储不同的 class 对象

泛型很棒,但是当您处理不同的(可能不相关的)对象、主题和错误时,使用泛型可能是错误的方法,因为查询和实际数据将大不相同。

将您的数据分开

let subjects = List<SubjectClass>()

let mistakes = List<MistakeClass>()

of 如果有一些联系就把它变成一个 class

class SubjectClass: Object {
    @objc dynamic var subject_name = ""
    @objc dynamic var is_mistake = false
}

如果一个主题可能有很多错误

class SubjectClass: Object {
    @objc dynamic var subject_name = ""
    let allMyMistakes = List<MistakeClass<>
}

有关一些数据建模信息,请查看 and then a fantasic answer from @DávidPásztor