Есть ли способ только частично создать объект из JSON в Swift? - PullRequest
1 голос
/ 07 ноября 2019

Я создаю приложение-визитку SwiftUI, и у меня нет проблем с использованием Codable и следую технике, которую Apple продемонстрировала со своим учебным приложением landmarks для импорта данных JSON для создания их массива объектов.

Однако два свойства моих объектов флэш-карты не нужно загружать из JSON, и я мог бы свести к минимуму текст, необходимый в файле JSON, если бы мог инициализировать эти значения отдельно вместо загрузки их из JSON. Проблема в том, что я не могу получить данные JSON для загрузки без ошибки, если они не отображаются точно на ВСЕ свойства объекта, даже если отсутствующие свойства жестко запрограммированы со значениями.

Вот моя объектная модель:

import SwiftUI

class Flashcard: Codable, Identifiable {
    let id: Int
    var status: Int
    let chapter: Int
    let question: String
    let answer: String
    let reference: String
}

Вот JSON, который работает:

[
  {
    "id": 1,
    "status": 0,
    "chapter": 1,
    "question": "This is the question",
    "answer": "This is the answer",
    "reference": "This is the reference"
  }
  //other card info repeated after with a comma separating each
]

Вместо того, чтобы "JD" и "статус" перечислены в JSON без необходимости, я бы предпочел изменить модель на что-то вроде этого:

import SwiftUI

class Flashcard: Codable, Identifiable {
    let id = UUID()
    var status: Int = 0

    //only load these from JSON:
    let chapter: Int
    let question: String
    let answer: String
    let reference: String
}

... и тогда я теоретически должен быть в состоянии исключить "id" и "status" из JSON (но я не могу). Есть ли простой способ сделать это, чтобы предотвратить неполное сопоставление ошибки JSON с объектом?

Ответы [ 2 ]

0 голосов
/ 07 ноября 2019

Вы можете использовать CodingKeys, чтобы определить, какие поля извлекать из JSON.

class Flashcard: Codable, Identifiable {
    enum CodingKeys: CodingKey {
       case chapter
       case question
       case answer
       case reference
    }

    let id = UUID()
    var status: Int = 0

    //only load these from JSON:
    let chapter: Int
    let question: String
    let answer: String
    let reference: String
}

The docuemntation has a good explanation (for once) of this under `Encoding and Decoding Custom Types`
0 голосов
/ 07 ноября 2019

Да, вы можете сделать это, установив ключи кодирования в вашем классе Codable. Просто оставьте те, которые вы не хотите обновлять с json.

class Flashcard: Codable, Identifiable {
    let id = UUID()
    var status: Int = 0
    let chapter: Int
    let question: String
    let answer: String
    let reference: String

    enum CodingKeys: String, CodingKey {
        case chapter, question, answer, reference
    }
}

Есть отличная статья HackingWithSwift о Codable здесь

...