类型 '' 不符合协议 'Decodable'/'Encodable'

Type '' does not conform to protocol 'Decodable'/'Encodable'

我有这段代码可以从 firestore 获取信息:

 struct Spty: Identifiable, Codable{
   @DocumentID var id: String? = UUID().uuidString
   var spty: String
   var r: NSNumber
   var g: NSNumber
   var b: NSNumber
}

 class SptyViewModel: NSObject, ObservableObject{
   @Published var specialities = [Spty]()
   @Published var search = ""
     func fetchData(){
      let db = Firestore.firestore()
        db.collection("specialities").addSnapshotListener { (querySnapshot, error) in
        guard let documents = querySnapshot else {return }
        self.specialities = documents.documents.compactMap { (doc) -> Spty? in
          let id = doc.documentID
            if  let spty = doc.get("spty") as? String,
            let r = doc.get("r") as?  NSNumber,
            let g = doc.get("g") as?  NSNumber,
            let b = doc.get("b") as?  NSNumber{
            
            return Spty(id: id, spty: spty, r: r , g: g , b: b )
            }
            else{
                return nil
            }
        }
      }
    }

   }

在看到 this video 之后,我开始对我的代码进行更改。但是,当我添加 Codable 时,我得到了这些错误

Type 'Spty' does not conform to protocol 'Decodable'

Type 'Spty' does not conform to protocol 'Encodable'

使用原生 Swift 类型(如 Double)而不是 NSNumber,并将其他代码与之对齐

struct Spty: Identifiable, Codable{
   @DocumentID var id: String? = UUID().uuidString
   var spty: String
   var r: Double
   var g: Double
   var b: Double
}

如您所见here“使类型可编码的最简单方法是使用已经可编码的类型声明其属性。这些类型包括标准库类型,如 String、Int 和 Double;以及基础类型,如 Date、Data 和 URL。任何其属性可编码的类型都自动符合 Codable,只需声明该一致性即可。”也就是说如果要使用codable,就要使用:

  1. 内置 Codable 类型 — String, Int, Double, Data, URL Array,

  2. 字典,可选如果包含可编码类型

    是可编码的

由于 NSNumber 不是 Codable 类型的一部分,因此您无法使用它。这个 link 和你的问题类似,你可以在那里看到相同的解释。