You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

Swift/SwiftUI中Realm如何使用同一模型将数据存入不同表

问题根因

你当前复用了同一个Question模型存储「选中题目」和「错题」两类业务数据,Realm查询Question.self时会返回所有该类型的存储对象,自然会同时返回两类题目数据,同个题目多次存储也会出现重复条目。

解决方案

方案1:新建独立错题表(推荐,业务隔离最清晰)

直接新增独立的错题模型,和原有Question字段完全一致,两类数据完全分开存储,不会互相干扰:

  1. 新增模型定义
struct WrongQuestion: Codable, Realmable, Hashable {
    var id: String = ""
    var question: String = ""
    var imageURL: String = ""
    var sections: [String : String] = [:]
    var correct: String = ""
    var isQuestionImage: Bool = false
    var isSectionImage: Bool = false
    var selected: String = ""
    // 可选:设置主键避免重复存储
    static func primaryKey() -> String? {
        return "id"
    }
}
  1. 修改存储、查询逻辑
// 存储错题
func saveWronQuestionToRealm(wrongQuestion: Question) {
    guard let realmReferance = try? Realm() else { return }
    // 转换为错题模型实例
    let wrongModel = WrongQuestion(id: wrongQuestion.id, question: wrongQuestion.question, imageURL: wrongQuestion.imageURL, sections: wrongQuestion.sections, correct: wrongQuestion.correct, isQuestionImage: wrongQuestion.isQuestionImage, isSectionImage: wrongQuestion.isSectionImage, selected: wrongQuestion.selected)
    do {
        try realmReferance.write({
            // 有主键的话用update参数避免重复写入
            realmReferance.add(wrongModel, update: .modified)
        })
    } catch let error {
        print(error)
    }
}

// 查询错题
func getWrongQuestionFromToRealm() -> [WrongQuestion]? {
    if let realmReferance = try? Realm() {
        let result = realmReferance.objects(WrongQuestion.self).reversed()
        return Array(result)
    }
    return nil
}

方案2:原有模型加标记字段(无需新建表)

给Question模型新增业务标记字段,存储时区分类型,查询时过滤即可:

  1. 修改Question模型
struct Question: Codable, Realmable, Hashable {
    var id: String = ""
    var question: String = ""
    var imageURL: String = ""
    var sections: [String : String] = [:]
    var correct: String = ""
    var isQuestionImage: Bool = false
    var isSectionImage: Bool = false
    var selected: String = ""
    // 新增标记字段:是否是错题
    var isWrong: Bool = false
}
  1. 修改存储、查询逻辑
// 存储错题
func saveWronQuestionToRealm(wrongQuestion: Question) {
    guard let realmReferance = try? Realm() else { return }
    // 先校验是否已存储过同id的错题,避免重复
    if let exist = realmReferance.object(ofType: Question.self, forPrimaryKey: wrongQuestion.id), exist.isWrong {
        return
    }
    do {
        try realmReferance.write({
            var newWrong = wrongQuestion
            newWrong.isWrong = true
            realmReferance.add(newWrong)
        })
    } catch let error {
        print(error)
    }
}

// 查询错题
func getWrongQuestionFromToRealm() -> [Question]? {
    if let realmReferance = try? Realm() {
        // 加过滤条件,只查标记为错题的条目
        let result = realmReferance.objects(Question.self).filter("isWrong == true").reversed()
        return Array(result)
    }
    return nil
}

内容的提问来源于stack exchange,提问作者Ufuk Köşker

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.09.30 16:09:01