[英]How to parse JSON to nested struct in Swift?
我將解析這個 JSON:
{
"status": 1,
"member": {
"id": "3",
"member_no": "1111",
"username": "uname",
"name": "name",
"email": "user@name.com",
"phone": "123 123",
"point": "100",
"expiry": "2019-09-22",
"grade": {
"id": "2",
"name": "Member"
}
}
}
我創建了這個結構:
struct User: Codable {
var status: Int?
var member: Member?
var msg: String?
struct Member: Codable {
var id: Int?
var member_no: String?
var username: String?
var name: String?
var email: String?
var phone: String?
var point: String?
var expiry: String?
var grade: Grade?
struct Grade: Codable {
var id: Int?
var name: String?
}
}
}
並使用它來解碼:
let decoder = JSONDecoder()
let user = try decoder.decode(User.self, from: data)
但我收到了這個錯誤:
無法讀取數據,因為它的格式不正確。
如果struct只有一層,那就沒問題了:
struct User: Codable {
var status: Int?
var msg: String?
}
如何編寫一個結構來匹配這個 JSON?
您可能想嘗試以下方法,這對我來說似乎很好用。
首先,我們需要為我們的結構User
創建CodingKeys
使用 codable 時,即使Member
內部的Member
和Grade
彼此嵌套。 您應該在 User 結構之外聲明這些結構。
正如您在下面看到的一樣 Member 和 Grade 應該符合Codable
,而 User 在擴展中符合Decodable
並通過將其用作容器來使用解碼器進行初始化。
此外,由於在您的 json 文件中,您在 User 和 Grade 中都將id
設為String
,但在您的代碼中,您將它們聲明為Int
因此我也修復了它們。
下面的代碼實現了我上面提到的 structs 和 CodingKeys,嘗試像我一樣接近或通過復制粘貼來嘗試,應該沒問題:
帶有 CodingKeys 的用戶結構:
struct User {
var status: Int?
var member: Member?
enum CodingKeys: String, CodingKey {
case status = "status"
case member = "member"
}
}
成員和等級結構:
struct Member: Codable {
var id: String?
var member_no: String?
var username: String?
var name: String?
var email: String?
var phone: String?
var point: String?
var expiry: String?
var grade: Grade?
}
struct Grade: Codable {
var id: String?
var name: String?
}
用戶擴展以符合 Codable:
extension User: Decodable {
init(from decoder: Decoder) throws {
let container = try decoder.container(keyedBy: CodingKeys.self)
self.status = try container.decode(Int?.self, forKey: .status)
self.member = try container.decode(Member?.self, forKey: .member)
}
}
現在創建一個解碼器並嘗試如下解碼:
let decoder = JSONDecoder()
let user = try! decoder.decode(User.self, from: data)
我希望這對你有幫助並且適合你
xcode 可能給你拋出了一個錯誤,說你的結構不符合可解碼協議,你不關心它:]
這是你的結構(模型)應該是什么樣子
struct User: Codable {
let status: Int?
let member: Member?
}
struct Member: Codable { let id, memberNo, username, name: String? let email, phone, point, expiry: String? let grade: Grade?
enum CodingKeys: String, CodingKey {
case id
case memberNo = "member_no"
case username, name, email, phone, point, expiry, grade
}
}
struct Grade: Codable { let id, name: String? }
嘗試這個
import Foundation
struct User: Codable {
let status: Int
let member: Member
}
struct Member: Codable {
let id, memberNo, username, name: String
let email, phone, point, expiry: String
let grade: Grade
enum CodingKeys: String, CodingKey {
case id
case memberNo = "member_no"
case username, name, email, phone, point, expiry, grade
}
}
struct Grade: Codable {
let id, name: String
}
struct User: Codable { var status: Int? var 成員:成員? var msg:字符串?
struct Member: Codable {
var id: String?
var member_no: String?
var username: String?
var name: String?
var email: String?
var phone: String?
var point: String?
var expiry: String?
var grade: Grade?
struct Grade: Codable {
var id: String?
var name: String?
}
}
}
您在 id 中有字符串而不是整數:
struct User: Codable {
var status: Int?
var member: Member?
struct Member: Codable {
var id: String?
var member_no: String?
var username: String?
var name: String?
var email: String?
var phone: String?
var point: String?
var expiry: String?
var grade: Grade?
struct Grade: Codable {
var id: String?
var name: String?
}
}
}
let decoder = JSONDecoder()
do {
let user = try decoder.decode(User.self, from: data)
} catch {
print(error)
}
聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.