标签: jsondecoder

如何使用未知密钥解码json

大家,如果字段之一未知,如何序列化json结构?

我的 json 是:

 {"brands":{"any":false,"19":{"is_all":false,"values":[185,182,178],"include":true},"23":{"is_all":false,"values":[198,199,201],"include":true}},"price":[2000,10000],"year":[1990,2018],"fuel_type":[1,2],"engine_capacity":[\"1.8\",\"4.8\"],"color":[1,2,3],"gearbox_id":[2],"is_georgia":false}
Run Code Online (Sandbox Code Playgroud)

但:

"19":{"is_all":false,"values":[185,182,178],"include":true}

"23":{"is_all":false,"values":[198,199,201],"include":true}

19 和 23 - 是字符串未知值,由 API 生成。

所以我的结构是:

    struct auto_order_model: Decodable {
        var brands: brand_details             <---- this is problem
        let price: [Int]
        let year: [Int]
        let fuel_type: [Int]
        let engine_capacity: [String]
        let color: [Int]
        let gearbox_id: [Int]
        let is_georgia: Bool
    }
    struct brand_details: Decodable {
        var any: Bool
        var brand_num: [models]?
    }
    struct models: Decodable {
        var is_all: Bool
        var values: [Int]
        var include: Bool
    }
Run Code Online (Sandbox Code Playgroud)

我像这样解码这个json:

    do {
        let data = …
Run Code Online (Sandbox Code Playgroud)

json swift jsondecoder

4
推荐指数
1
解决办法
1810
查看次数

当Swift是一个数组并且第一个项目与其他项目不同时,如何在Swift中解码JSON?

说JSON看起来像这样:

[
    {
        "name": "Spot",
        "breed": "dalmation"
    },
    {
        "color": "green",
        "eats": "lettuce"
    },
    {
        "color": "brown",
        "eats": "spinach"
    },
    {
        "color": "yellow",
        "eats": "cucumbers"
    }
]
Run Code Online (Sandbox Code Playgroud)

从API返回的JSON响应中的第一项始终是狗,而之后的所有项都是乌龟.因此项目0是狗,项目1到N-1是海龟.

我如何将其解析为我可以阅读的内容,例如:

struct Result: Codable {
    let dog: Dog
    let turtles: [Turtle]
}
Run Code Online (Sandbox Code Playgroud)

可能吗?

json struct swift jsondecoder

4
推荐指数
1
解决办法
798
查看次数

如何使用 JSONDecoder 解码未知类型的 JSON?

这是我的场景:我有一个快速的 WebSocket 服务器和一个 Javascript 客户端。通过同一个 WebSocket,我将发送对应于不同Codable 类型的各种对象。如果已知正确的类型,则解码很简单。对我来说,困难在于确定客户端发送的是哪种类型。我的第一个想法是使用如下所示的 JSON:

{type: "GeoMarker", 
 data: {id: "2",
        latitude: "-97.32432"
        longitude: "14.35436"}
}
Run Code Online (Sandbox Code Playgroud)

这样我就知道使用解码datalet marker = try decoder.decode(GeoMarker.self) 似乎很简单,但由于某种原因,我只是不知道如何将对象提取data为 JSON,以便我可以使用 GeoMarker 类型对其进行解码。

我想出的另一个解决方案是创建一个中间类型,如下所示:

struct Communication: Decodable {
let message: String?
let markers: [GeoMarker]?
let layers: [GeoLayer]?
}
Run Code Online (Sandbox Code Playgroud)

这样我就可以发送以下格式的 JSON:

{message: "This is a message",
 markers: [{id: "2",
           latitude: "-97.32432"
           longitude: "14.35436"},
           {id: "3",
           latitude: "-67.32432"
           longitude: "71.35436"}]
}
Run Code Online (Sandbox Code Playgroud)

并使用let com = try decoder.decode(Communication.self)和解包可选的消息、标记和图层变量。这可行,但看起来很笨重,特别是当我需要更多类型时。说完一切之后,我可能最终需要 8-10 个。

我已经考虑过这个问题,但我觉得我没有想出一个令人满意的解决方案。会有更好的方法吗?对于我不知道的这种事情是否有一个标准? …

json websocket swift jsondecoder

4
推荐指数
1
解决办法
3782
查看次数

swift parse json-无法读取数据,因为格式不正确

这是我的JSON响应值:

 {
   "_embedded": {
    "task": [
        {
            "_embedded": {
                "variable": [
                    {
                        "_links": {
                            "self": {
                                "href": "/process-instance/412a03b7-06ae-11ea-8860-120ef5ab2c25/variables/loanAmount"
                            }
                        },
                        "_embedded": null,
                        "name": "loanAmount",
                        "value": "650000",
                        "type": "String",
                        "valueInfo": {}
                    }
                ]
            },
            "id": "412a2aca-06ae-11ea-8860-120ef5ab2c25",
            "name": "Quick Evaluation",
            "assignee": "demo",
            "created": "2019-11-14T07:13:27.558+0000",
            "processDefinitionId": "quickEvaluation:1:129ce2b1-0616-11ea-8860-120ef5ab2c25"

        }

    ]
},
 "count": 13
}
Run Code Online (Sandbox Code Playgroud)

这是struct可编码的代码:

import Foundation

public struct TaskID: Codable {
    let embedded: Embedded
}

public struct Embedded: Codable {
    let task: [Task]
}

public struct Task : Codable {

    let embedded: EmbeddedVariable …
Run Code Online (Sandbox Code Playgroud)

json ios swift alamofire jsondecoder

4
推荐指数
1
解决办法
260
查看次数

如何使用 JSONDecoder 解码自定义 JSON 值

后端返回位置的自定义 JSON 值。如示例所示:

{
    "location": (54.000000, 21.000000)
}
Run Code Online (Sandbox Code Playgroud)

为了解析 JSON,我使用以下代码:

let json = """
{
    "location": (54.000000, 21.000000)
}
"""    
struct Location: Codable {
    var latitude: Double
    var longitude: Double
}
let dataJson = json.data(using: .utf8)!
let location = try? JSONDecoder().decode(Location.self, from: dataJson)
Run Code Online (Sandbox Code Playgroud)

当我尝试使用 JSONDecoder 创建 Location 对象时,出现错误:给定的数据不是有效的 JSON。

dataCorrupted(Swift.DecodingError.Context(codingPath: [], debugDescription: "The given data was not valid JSON.", underlyingError: Optional(Error Domain=NSCocoaErrorDomain Code=3840 "Invalid value around character 18." UserInfo={NSDebugDescription=Invalid value around character 18.})))
Run Code Online (Sandbox Code Playgroud)

我知道它不是有效的 JSON。重写哪些方法可以解析无效的 JSON 值?

swift4 jsondecoder

3
推荐指数
1
解决办法
7976
查看次数

JSONDecoder 总是返回“没有与键 CodingKeys 关联的值”

我使用以下解码结构来解码来自服务器的数据,但它总是返回“没有与密钥 CodingKeys 关联的值”。请看下面的代码

struct UserDecode: Codable {

var user: User?
var result: String?

private enum CodingKeys: String, CodingKey {
    case user = "Records"
    case result = "Result"
}

init(from decoder: Decoder) throws {
    do {
        let values = try decoder.container(keyedBy: CodingKeys.self)
        result = try values.decode(String.self, forKey: .result)
        user = try values.decode(User.self, forKey: .user)
    } catch {
        print(error.localizedDescription)
    }
}
}

struct User: Codable {

var mobile: Int?
var userId: Int?
var name: String?

private enum CodingKeys: String, CodingKey {
    case …
Run Code Online (Sandbox Code Playgroud)

ios swift jsondecoder

3
推荐指数
1
解决办法
5046
查看次数

实例成员“decode”不能用于类型“JSONDecoder”;您是否打算使用这种类型的值

我实现 JSONDecoder 以从 Wordpress json 获取 JSON 数据,我的结构位于另一个 swift 文件中,我收到此错误,这是我的代码。在让文章上我收到错误

URLSession.shared.dataTask(with: url!){ (data,response ,err) in
        guard let data = data else{return}
        let article = JSONDecoder.decode(LatestArticleModel , from: data)

    }.resume()
Run Code Online (Sandbox Code Playgroud)

最新文章模型.swift

struct LatestArticleModel : Decodable {

    var id: Int
    var date: String
    var link: String
    var title_rendered :String
    var author: Int
    var category: Int
    var img_link: String
    var content_rendered: String
    var exerpt_rendered: String


}
Run Code Online (Sandbox Code Playgroud)

ios swift jsondecoder

3
推荐指数
1
解决办法
6162
查看次数

Swift 通用 Json 解析器

我有一个通用的 JSON 解析器,可以解码数组

class JSONParserFromStruct {
    typealias result<T> = (Result<[T], Error>) -> Void

    func downloadList<T: Decodable>(of _: T.Type,
                                    from data: Data,
                                    completion: @escaping result<T>) {
        do {
            let decodedData: [T] = try! JSONDecoder().decode([T].self, from: data)
            completion(.success(decodedData))
        } catch {
            completion(.failure(DataError.decodingError))
        }
    }
}
Run Code Online (Sandbox Code Playgroud)

捆绑包中的 Users.json 文件

{
    "name": "Taylor Swift"
}
Run Code Online (Sandbox Code Playgroud)

像这样调用它:

func performRequest() {
    let url = Bundle.main.url(forResource: "Users", withExtension: "json")!
    let data = try! Data(contentsOf: url)
    genericParser.downloadList(of: User.self, from: data) { result in
        switch result {
        case let …
Run Code Online (Sandbox Code Playgroud)

generics json json-deserialization swift jsondecoder

3
推荐指数
1
解决办法
2959
查看次数

字典的可解码 keyDecodingStrategy 自定义处理

我有以下 JSON 对象:

{
  "user_name":"Mark",
  "user_info":{
    "b_a1234":"value_1",
    "c_d5678":"value_2"
  }
}
Run Code Online (Sandbox Code Playgroud)

我已经JSONDecoder这样设置了:

let decoder = JSONDecoder()
decoder.keyDecodingStrategy = .convertFromSnakeCase
Run Code Online (Sandbox Code Playgroud)

我的Decodable对象看起来像这样:

struct User: Decodable {
    let userName: String
    let userInfo: [String : String]
}
Run Code Online (Sandbox Code Playgroud)

我面临的问题是该.convertFromSnakeCase策略正在应用于字典的键,我希望这种情况不会发生。

// Expected Decoded userInfo
{
  "b_a1234":"value_1",
  "c_d5678":"value_2"
}

// Actual Decoded userInfo
{
  "bA1234":"value_1",
  "cD5678":"value_2"
}
Run Code Online (Sandbox Code Playgroud)

我研究过使用自定义keyDecodingStrategy(但没有足够的信息来以不同方式处理字典)以及我的自定义初始值设定项Decodable结构的自定义初始值设定项(似乎此时键已经被转换)。

处理此问题的正确方法是什么(仅为字典创建键转换异常)?

注意:我更愿意保留蛇形大小写转换策略,因为我的实际 JSON 对象在蛇形大小写中有很多属性。我当前的解决方法是使用 CodingKeys 枚举手动进行蛇形大小写转换。

json swift codable decodable jsondecoder

2
推荐指数
1
解决办法
2569
查看次数

Swift Codable:使用父级的键作为值

我有一个 JSON,其 ID 在根级别:

{
    "12345": {
        "name": "Pim"
    },
    "54321": {
        "name": "Dorien"
    }
}
Run Code Online (Sandbox Code Playgroud)

我的目标是使用 Codable 创建一个同时具有 name 和 ID 属性的 User 对象数组。

struct User: Codable {
    let id: String
    let name: String
}
Run Code Online (Sandbox Code Playgroud)

我知道如何使用带有单个根级别密钥的Codable ,并且知道如何使用未知密钥。但我在这里尝试做的是两者的结合,我不知道下一步该做什么。

这是我到目前为止得到的:(您可以将其粘贴到 Playground 中)

import UIKit

var json = """
{
    "12345": {
        "name": "Pim"
    },
    "54321": {
        "name": "Dorien"
    }
}
"""

let data = Data(json.utf8)

struct User: Codable {
    let name: String
}

let decoder = JSONDecoder() …
Run Code Online (Sandbox Code Playgroud)

swift codable decodable jsondecoder

2
推荐指数
1
解决办法
1728
查看次数