Swift의 [String: Any]를 디코딩하는 방법은 무엇입니까?
[String: Any]
로 디코딩해야 합니까? 다음은 이 작업을 수행하는 방법입니다.요구 사항
대답은 Any
유형을 사용하여 이 작업을 수행할 수 없다는 것입니다. Any
보다 구체적인 것을 지정해야 합니다.
Dictionary is automatically decodable if its elements are decodable. Type Any
is not decodable.
그러나 대답을 찾고 있다면 실제로 어떻게 든 처리해야 하는 일종의 JSON이 있음을 의미합니다. 주제는 [Any]
와 같은 배열과도 관련이 있습니다.
해결책
Any
유형의 가능한 값의 유한 수를 지정해야 합니다. 예를 들어 다음과 같은 두 가지 다른 구조가 있을 것으로 예상합니다.
struct Payload: Codable {
let id: String
let eventName: String
let metadata: [Metadata]
}
struct Metadata: Codable {
let name: String?
let price: Double?
let rating: Int?
}
하지만 물론 당신은 할 수 없습니다
let decodedData = try JSONDecoder().decode([String: Any].self, from: json.data(using: .utf8)!)
사용된 유형Any
이 있기 때문입니다.
우선 이 사전의 JSON이 어떻게 생겼는지 알아야 합니다. 다음과 같이 될 것입니다.
{
"keyNumber1": {
"type": "payload",
"data": {
"id": "someId1",
"eventName": "Event Name 1",
"metadata": []
}
},
"keyNumber2": {
"type": "metadata",
"data": {
"name": "Metadata Name",
"price": 123.4,
"rating": 100
}
}
}
그런 다음 다음과 같이 enum
유형 대신 Any
를 정의해야 하기 때문에 간단합니다.
enum DataType: String, Codable {
case payload
case metadata
}
enum MyValue: Decodable {
case payload(_ payload: Payload)
case metadata(_ metadata: Metadata)
private enum CodingKeys: String, CodingKey {
case `type`
case `data`
}
init(from decoder: Decoder) throws {
let map = try decoder.container(keyedBy: CodingKeys.self)
let dataType = try map.decode(DataType.self, forKey: .type)
switch dataType {
case .payload:
self = .payload(try map.decode(Payload.self, forKey: .data))
case .metadata:
self = .metadata(try map.decode(Metadata.self, forKey: .data))
}
}
}
다음 코드를 사용하여 JSON을 디코딩합니다.
let decodedData = try JSONDecoder().decode([String: MyValue].self, from: json.data(using: .utf8)!)
전체 플레이그라운드 코드:
Reference
이 문제에 관하여(Swift의 [String: Any]를 디코딩하는 방법은 무엇입니까?), 우리는 이곳에서 더 많은 자료를 발견하고 링크를 클릭하여 보았다
https://dev.to/absoftware/how-to-make-swift-s-string-any-decodable-5c6n
텍스트를 자유롭게 공유하거나 복사할 수 있습니다.하지만 이 문서의 URL은 참조 URL로 남겨 두십시오.
우수한 개발자 콘텐츠 발견에 전념
(Collection and Share based on the CC Protocol.)
Dictionary is automatically decodable if its elements are decodable. Type Any
is not decodable.
Any
유형의 가능한 값의 유한 수를 지정해야 합니다. 예를 들어 다음과 같은 두 가지 다른 구조가 있을 것으로 예상합니다.struct Payload: Codable {
let id: String
let eventName: String
let metadata: [Metadata]
}
struct Metadata: Codable {
let name: String?
let price: Double?
let rating: Int?
}
하지만 물론 당신은 할 수 없습니다
let decodedData = try JSONDecoder().decode([String: Any].self, from: json.data(using: .utf8)!)
사용된 유형
Any
이 있기 때문입니다.우선 이 사전의 JSON이 어떻게 생겼는지 알아야 합니다. 다음과 같이 될 것입니다.
{
"keyNumber1": {
"type": "payload",
"data": {
"id": "someId1",
"eventName": "Event Name 1",
"metadata": []
}
},
"keyNumber2": {
"type": "metadata",
"data": {
"name": "Metadata Name",
"price": 123.4,
"rating": 100
}
}
}
그런 다음 다음과 같이
enum
유형 대신 Any
를 정의해야 하기 때문에 간단합니다.enum DataType: String, Codable {
case payload
case metadata
}
enum MyValue: Decodable {
case payload(_ payload: Payload)
case metadata(_ metadata: Metadata)
private enum CodingKeys: String, CodingKey {
case `type`
case `data`
}
init(from decoder: Decoder) throws {
let map = try decoder.container(keyedBy: CodingKeys.self)
let dataType = try map.decode(DataType.self, forKey: .type)
switch dataType {
case .payload:
self = .payload(try map.decode(Payload.self, forKey: .data))
case .metadata:
self = .metadata(try map.decode(Metadata.self, forKey: .data))
}
}
}
다음 코드를 사용하여 JSON을 디코딩합니다.
let decodedData = try JSONDecoder().decode([String: MyValue].self, from: json.data(using: .utf8)!)
전체 플레이그라운드 코드:
Reference
이 문제에 관하여(Swift의 [String: Any]를 디코딩하는 방법은 무엇입니까?), 우리는 이곳에서 더 많은 자료를 발견하고 링크를 클릭하여 보았다 https://dev.to/absoftware/how-to-make-swift-s-string-any-decodable-5c6n텍스트를 자유롭게 공유하거나 복사할 수 있습니다.하지만 이 문서의 URL은 참조 URL로 남겨 두십시오.
우수한 개발자 콘텐츠 발견에 전념 (Collection and Share based on the CC Protocol.)