如何解析这个复杂的嵌套Json

如何解析这个复杂的嵌套Json,json,swift,swift4.2,jsondecoder,Json,Swift,Swift4.2,Jsondecoder,Json是有效的,但返回的Json的代码和结构为零 遇到的问题: 在JSonDecoder.decode():它返回了这个错误消息: keyNotFound(编码键(stringValue:“项”,intValue:nil),Swift.DecodingError.Context(编码路径:[[U JSONKey(stringValue:“项”,intValue:nil),[U JSONKey(stringValue:“索引0”,intValue:0)],调试说明:“没有与键编码键相关的值(st

Json是有效的,但返回的Json的代码和结构为零

遇到的问题:

  • 在JSonDecoder.decode():它返回了这个错误消息:

    keyNotFound(编码键(stringValue:“项”,intValue:nil),Swift.DecodingError.Context(编码路径:[[U JSONKey(stringValue:“项”,intValue:nil),[U JSONKey(stringValue:“索引0”,intValue:0)],调试说明:“没有与键编码键相关的值(stringValue:“项”,intValue:nil)(“项”)”,底层错误:nil))

  • 如何从Json获取这些a)图像b)位置

  • 谢谢

    这是密码

    func getJsonMapData(){
            
            guard let mapUrl = URL(string: "https://xxxxxx/traffic-images") else { return }
            
            URLSession.shared.dataTask(with: mapUrl) { (data, response, error) in
            
                guard error == nil else { return}
    
                guard let data = data else { return}
             
                //- problem: 
    
                do {
    
                    let LocationArrDict = try JSONDecoder().decode([String:[Location]].self, from: data)else{
                    
                    print(LocationArrDict)              
      
                } catch {
    
                  print(error)
                }
               
            }.resume()
        }
    
    
    
    //------------- return Json String:
    
    {
       "items":[
          {
             "timestamp":"2020-12-05T08:45:43+08:00",
             "cameras":[
                {
                   "timestamp":"2020-11-05T08:42:43+08:00",
                   "image":"https://xxxxxxxxx/traffic-images/2020/12/2ab06cd8-4dcf-434c-b758-804e690e57db.jpg",
                   "location":{
                      "latitude":1.29531332,
                      "longitude":103.871146
                   },
                   "camera_id":"1001",
                   "image_metadata":{
                      "height":240,
                      "width":320,
                      "md5":"c9686a013f3a2ed4af61260811661fc4"
                   }
                },
                {
                   "timestamp":"2020-11-05T08:42:43+08:00",
                   "image":"https://xxxxxxxxxx/traffic-images/2020/12/9f6d307e-8b05-414d-b27d-bf1414aa2cc7.jpg",
                   "location":{
                      "latitude":1.319541067,
                      "longitude":103.8785627
                   },
                   "camera_id":"1002",
                   "image_metadata":{
                      "height":240,
                      "width":320,
                      "md5":"78060d8fbdd241adf43a2f1ae5d252b1"
                   }
                 },
    
                        ........
    
                {
                   "timestamp":"2020-12-05T08:42:43+08:00",
                   "image":"https://xxxxxx/traffic-images/2020/12/98f64fe6-5985-4a8a-852f-0be24b0a6271.jpg",
                   "location":{
                      "latitude":1.41270056,
                      "longitude":103.80642712
                    },
                     "camera_id":"9706",
                     "image_metadata":{
                      "height":360,
                      "width":640,
                      "md5":"f63d54176620fa1d9896fa438b3cc753"
                    }
                }
              ]
            }
      
           ],
      
          "api_info":{
             "status":"healthy"
           }
    }
    
    
    
    //------------ struct for the return Json result:
    
    
    // MARK: - Location
    
    struct Location: Codable {
        let items: [Item]
        let apiInfo: APIInfo
    
        enum CodingKeys: String, CodingKey {
            case items
            case apiInfo = "api_info"
        }
    }
    
    // MARK: - APIInfo
    struct APIInfo: Codable {
        let status: String
    }
    
    // MARK: - Item
    struct Item: Codable {
        let timestamp: Date
        let cameras: [Camera]
    }
    
    // MARK: - Camera
    struct Camera: Codable {
        let timestamp: Date
        let image: String
        let location: LocationClass
        let cameraID: String
        let imageMetadata: ImageMetadata
    
        enum CodingKeys: String, CodingKey {
            case timestamp, image, location
            case cameraID = "camera_id"
            case imageMetadata = "image_metadata"
        }
    }
    
    // MARK: - ImageMetadata
    struct ImageMetadata: Codable {
        let height, width: Int
        let md5: String
    }
    
    // MARK: - LocationClass
    struct LocationClass: Codable {
        let latitude, longitude: Double
    }
    
    
    
    ``
    
    错误#1:要解码的类型错误它必须是
    位置.self

    错误2:要将ISO日期解码为
    date
    ,必须添加
    .iso8601
    日期解码策略

    do {
        let decoder = JSONDecoder()
        decoder.dateDecodingStrategy = .iso8601
        let locationArrDict = try decoder.decode(Location.self, from: data)
        print(locationArrDict)              
    
    } catch {
       print(error)
    }
    

    您可以将表示URL的字符串直接解码到
    URL

    您必须创建数据模型,并将它们描述为您期望收到的响应。我将根据您的json为您提供一个简单的示例,您将如何对其进行解码

    首先,为了使用
    JSONDecoder
    解码JSON,您的模型必须符合
    Decodable
    协议。然后你必须创建那些模型

    struct项:可解码{
    让时间戳:日期
    //让摄像机:[……]
    }
    结构apinfo:可解码{
    枚举状态:字符串,可解码{
    病例健康
    }
    让状态:状态
    }
    结构响应:可解码{
    出租项目:[项目]
    让我们看看apinfo:apinfo
    }
    
    然后您必须配置
    JSONDecoder
    并解码该JSON。我们可以清楚地看到,您的JSON使用了
    snake\u case
    命名约定,而这不是
    jsondeconder
    的默认约定,因此您必须设置它。同样的情况也适用于日期-它用于
    iso8601
    表示标准

    让jsonDecoder=jsonDecoder()
    jsonDecoder.dateDecodingStrategy=.iso8601
    jsonDecoder.keyDecodingStrategy=.convertFromSnakeCase
    
    最后,你有你解码它

    do{
    让response=尝试jsonDecoder.decode(response.self,from:jsonData)
    打印(答复)
    }抓住{
    打印(错误)
    }
    
    不要
    尝试?
    ,永远不要
    尝试?
    Codable
    环境中忽略错误。捕捉错误并打印它。至少有两个。您发布的JSON似乎无效。括号不平衡。@Sweeper,json结果太长,无法在此处显示。我检查了在线json验证程序。我尝试[Location].self[String:[Location]].self或Location.self,它们不起作用。无论实际的JSON是否太长,都应该显示一个。显示重现问题的最短、有效的JSON。@请参阅更新。json结果如上图所示。代码部分指出了这个问题。让我研究一下您的解决方案,然后很快回到这里。似乎我在使用您发布的代码->类型不匹配(swift.double,swift.decoding error.Context)后出错了……“预期解码double,但改为查找/dat”你真的将解码器实例用于日期解码策略吗?错误表明你没有。你的解决方案有效。我不想一下子问这么多问题。我认为我的json解析需要很多帮助才能学习。我认为这个练习将提高我对json的理解。我有两个关于json的问题。谢谢你的帮助:对不起,我我不熟悉谷歌地图API