我正在加載用戶通知,有不同的通知型別(例如,評論,關注),我需要根據他們的“型別”屬性解碼每個通知,但我是采用這種方法的新手,并且整天都在試圖弄清楚如何去做這個...
現在我在 NotificationsEnum 中不斷收到解碼錯誤,我認為這是因為我不知道如何訪問陣列中回傳的每個物件內的type屬性。
我嘗試使用這個 SO question & answer從嵌套容器中解碼 JSON 并動態檢查其型別以快速進行型別轉換,但它與類有關,我正在使用結構。
如何根據它們的型別屬性解碼每個物件?我覺得我需要弄清楚如何以某種方式實作nestedUnkeyedContainer和nestedContainer,但我很難讓它作業。
另外,在解碼作業后,如何將所有這些物件放在同一個陣列中?它會是泛型,因為我會打開它們的型別以將通知路由到不同的通知視圖......??
謝謝
我需要根據型別解碼不同的 JSON 活動
[
{
_id: 61dc9bde82d0715,
type: 'like',
username: 'testuser1',
likeId: 61dcb2d0712
},
{
_id: 61dc9bde82d0715,
type: 'follow',
username: 'testuser2',
followId: 61dc9bd2d0712
},
{
_id: 61dc9b2d0715,
type: 'comment',
username: 'testuser3',
commentId: 61dc9bb2d0712
}
]
組態檔/父資料模型
struct ProfileData: Decodable {
**otherProperties**
var notifications: [NotificationsEnum]
// ^ Is this correct type? Was thinking I might need some kind of generic array??
}
// 我如何在這里實作nestedUnkeyedContainer 和nestedContainer ???
enum NotificationsEnum: Decodable {
enum DecodingError: Error {
case wrongJSON
}
case like(LikeActivity)
case comment(CommentActivity)
case follow(FollowActivity)
enum CodingKeys: String, CodingKey {
case like = "like"
case comment = "comment"
case follow = "follow"
}
init(from decoder: Decoder) throws {
let container = try decoder.container(keyedBy: CodingKeys.self)
switch container.allKeys.first {
case .like:
let value = try container.decode(LikeActivity.self, forKey: .like)
self = .like(value)
case .comment:
let value = try container.decode(CommentActivity.self, forKey: .comment)
self = .comment(value)
case .follow:
let value = try container.decode(FollowActivity.self, forKey: .follow)
self = .follow(value)
case .none:
throw DecodingError.wrongJSON
}
}
}
楷模
struct LikeActivity: Codable {
let id: String
let type: String
let username: String
let likeId: String
}
struct CommentActivity: Codable {
let id: String
let type: String
let username: String
let commentId: String
}
struct FollowActivity: Codable {
let id: String
let type: String
let username: String
let followId: String
}
uj5u.com熱心網友回復:
您要做的是首先解碼,type然后使用切換解碼值并使用相同的decoder物件初始化相應的型別。
您也可以因此縮短 CodingKeys 列舉,因為我們只使用一個鍵。
enum CodingKeys: String, CodingKey {
case type
}
init(from decoder: Decoder) throws {
let container = try decoder.container(keyedBy: CodingKeys.self)
let type = try container.decode(String.self, forKey: .type)
switch type {
case "like":
self = try .like(LikeActivity(from: decoder))
case "comment":
self = try .comment(CommentActivity(from: decoder))
case "follow":
self = try .follow(FollowActivity(from: decoder))
default:
throw DecodingError.wrongJSON
}
}
您還可以為type值創建一個列舉
enum ActivityType: String {
case like, comment, follow
}
然后switch在init(from:)變
switch ActivityType(rawValue: type) {
case .like:
self = try .like(LikeActivity(from: decoder))
case .comment:
self = try .comment(CommentActivity(from: decoder))
case .follow:
self = try .follow(FollowActivity(from: decoder))
default:
throw DecodingError.wrongJSON
}
轉載請註明出處,本文鏈接:https://www.uj5u.com/houduan/407929.html
標籤:
上一篇:設定多天時本地通知未觸發
下一篇:當我點擊沒有導航的按鈕時,如何在xib(ViewController)中打開xib(ViewController)
