【问题标题】:Use Swifty JSON to parse array使用 Swifty JSON 解析数组
【发布时间】:2016-12-10 15:01:53
【问题描述】:

这是我要解析的 json(示例):

[
  {
    "id": 1,
    "name": "Team name",
    "shower": {
      "id": 1,
      "status": 1,
      "startLocation": {
        "id": 1,
        "name": "abc 16"
      }
    }
  },
  {
    "id": 2,
    "name": "Team name",
    "shower": {
      "id": 2,
      "status": 1,
      "startLocation": {
        "id": 1,
        "name": "efg 16"
      }
    }
  }
]

如您所见,它是一个(团队)数组。 我需要让每个团队都参与其中。

经过多次尝试,我尝试使用SwiftyJSON,因为我认为它会更容易。但是,它对我不起作用。

这是我尝试过的:

let array = JSON(response)  

// print each subJSON in array
for team in array.arrayValue {                    
  print(team)                    
}

但循环不起作用。它根本不进入循环。 也许它不明白我的json是一个数组。

我可以在调试器中看到数组对象。它看起来像这样:

如何获取这些子 JSON?

谢谢。

【问题讨论】:

  • 您的 JSON 无效。 "name": "abc 16" 之后的行和之后的行不应该有逗号。
  • 使用jsoneditoronline.org 这个来验证你的json。它在您的 json 字符串中显示错误。
  • 要求您的服务器团队在每个创建问题的值之前删除额外的斜杠,因为 json 是键值对,但它似乎是无法获取的字符串
  • 谢谢大家,我编辑并修复了 json 示例。
  • 修复json字符串后还是不行?

标签: ios json swift swifty-json


【解决方案1】:

我认为你应该使用

let array = JSON(parseJSON: response) 

而不是

let array = JSON(response)

【讨论】:

  • 我试过你的建议@Arjuna,它没有奏效。仍然没有进入循环。谢谢,
【解决方案2】:

SwiftyJSON 包含将 JSON 字符串解析为 JSON 对象的方法,请查看documentation

/**
 Parses the JSON string into a JSON object
 - parameter json: the JSON string
 - returns: the created JSON object
*/

 public init(parseJSON jsonString: String) {
   if let data = jsonString.data(using: .utf8) {
                self.init(data)
            } else {
                self.init(NSNull())
            }        
   }       


/**
 Creates a JSON from JSON string
 - parameter string: Normal json string like '{"a":"b"}'

 - returns: The created JSON
 */
@available(*, deprecated: 3.2, message: "Use instead `init(parseJSON: )`")
public static func parse(json: String) -> JSON {
    return json.data(using: String.Encoding.utf8)
        .flatMap{ JSON(data: $0) } ?? JSON(NSNull())
}

或者您也可以将子字符串转换为子对象,例如

斯威夫特 3:

let dataFromString = response.data(using: .utf8)
let jsonArray = JSON(data: dataFromString!)

【讨论】:

    【解决方案3】:

    在以下示例中,我将团队名称保存在一个数组中。我已经测试过了。

    var names = [String]()
    if let array = json.array {
        for i in 0..<array.count {
            let name = array[i]["name"]
            names.append(name.stringValue)
        }
    }
    
    print(names) // ["Team name", "Team name"]
    

    【讨论】:

      【解决方案4】:

      这是 Swift 5 的答案。在我的情况下,数据响应如下所示:

      [
        {
          "Name": "Some Type",
          "Data": [
            {
              "ParentId": 111,
              "Code": "Personal",
              "SortOrder": 1,
              "Name": "Personal",
              "Id": 323
            },
            {
              "ParentId": null,
              "Code": "Work",
              "SortOrder": 2,
              "Name": "Work",
              "Id": 324
            }
          ],
          "KeyType": "Integer"
        },
        {
          "Name": "Phone Type",
          "Data": [
            {
              "ParentId": null,
              "Code": "Phone",
              "SortOrder": 1,
              "Name": "Phone",
              "Id": 785
            },
            {
              "ParentId": null,
              "Code": "Cell",
              "SortOrder": 2,
              "Name": "Cell",
              "Id": 786
            },
            {
              "ParentId": null,
              "Code": "Fax",
              "SortOrder": 3,
              "Name": "Fax",
              "Id": 787
            },
            {
              "ParentId": null,
              "Code": "Home",
              "SortOrder": 4,
              "Name": "Home",
              "Id": 788
            },
            {
              "ParentId": null,
              "Code": "Office",
              "SortOrder": 5,
              "Name": "Office",
              "Id": 789
            }
          ],
          "KeyType": "Integer"
        }
      ]
      

      我是用下面的代码处理的。

      struct responseObjectClass:BaseModel {
          var responsearray: [arrayData]? = nil
      
          init(json: JSON) {
              responsearray = json.arrayValue.map { arrayData(json: $0) }
          }
      }
      
      struct arrayData:BaseModel {
          let Name: String?
             var DataValue: [DataLookup]? = nil
             let KeyType: String?
             
             init(json: JSON) {
                 Name = json["Name"].stringValue
                 DataValue = json["Data"].arrayValue.map { DataLookup(json: $0) }
                 KeyType = json["KeyType"].stringValue
             }
      }
      
      struct DataLookup:BaseModel {
          
          
          let ParentId: Any?
          let Code: String?
          let SortOrder: Int?
          let Name: String?
          let Id: Int?
          
          init(json: JSON) {
              ParentId = json["ParentId"]
              Code = json["Code"].stringValue
              SortOrder = json["SortOrder"].intValue
              Name = json["Name"].stringValue
              Id = json["Id"].intValue
          }
      }
      

      BaseModel 是可选的,它只用于 init Json。

      protocol BaseModel {
        init(json: JSON)
      }
      

      【讨论】:

        【解决方案5】:

        没有 SwiftyJSON

        以下是有效的 JSON

        data.json 文件

        [{
          "id": 1,
          "name": "Team name",
          "shower": {
                "id": 1,
                "status": 1,
                "startLocation": {
          "id": 1,
          "name": "abc 16"
                }
          }
          }, {
          "id": 2,
          "name": "Team name",
          "shower": {
                "id": 2,
                "status": 1,
                "startLocation": {
          "id": 1,
          "name": "efg 16"
                }
          }
        }]
        

        以下是读取 json 的代码。

        if let path = Bundle.main.path(forResource: "data", ofType: "json") {
                let url = URL(fileURLWithPath: path)
                do {
                    let data = try Data(contentsOf: url)
                    if let jsonArray = try JSONSerialization.jsonObject(with: data, options: .allowFragments) as? NSArray {
                        for (_, item) in jsonArray.enumerated() {
                            let itemDict = item as! NSDictionary
                            let id = itemDict["id"] as! Int
                            let name = itemDict["name"] as! String
                            let shower = itemDict["shower"] as! NSDictionary
        
                            let showerId = shower["id"] as! Int
                            let showerStatus = shower["status"] as! Int
                            let startLocation = shower["startLocation"] as! NSDictionary
        
        
                            let startLocationId = startLocation["id"] as! Int
                            let startLocationName = startLocation["name"] as! String
        
                        }
                    }
                } catch {
                    print("Error: \(error.localizedDescription)")
                }
        }
        

        【讨论】:

          【解决方案6】:

          这对我有用:

             // Convert JSON to Array
              func JSONToArray(_ json: String) -> Array<Any>? {
                  if let data = json.data(using: String.Encoding.utf8) {
                      do {
                          return try JSONSerialization.jsonObject(with: data, options: []) as? Array
                      } catch let error as NSError {
                          print(error)
                      }
                  }
                  return nil
              }
          

          使用此函数后,我可以循环遍历子 JSON。

          谢谢。

          【讨论】:

            猜你喜欢
            • 1970-01-01
            • 1970-01-01
            • 2018-07-27
            • 1970-01-01
            • 2021-12-22
            • 1970-01-01
            • 1970-01-01
            • 1970-01-01
            • 1970-01-01
            相关资源
            最近更新 更多