将序列化JSON加载到表中?

时间:2016-11-13 14:47:13

标签: json swift serialization alamofire

我非常难以绕过这个过程,我已经进行了API调用并收到了JSON,然后我使用模型来序列化JSON,以便它可以在我的View Controller Table中轻松使用,但我如何在View Controller中调用API以使结果适合我的序列化模型存在问题。我希望我能正确解释一下吗?

以下是我的API请求的代码:

open class ApiService: NSObject {

    open func getData(completionHandler: @escaping (NSDictionary?, NSError?) -> Void) -> Self {

        let requestUrl = "https://wger.de/api/v2/exercise/?format=json"

        Alamofire.request(requestUrl, method: .get, encoding: URLEncoding.default)
            .responseJSON { response in
                switch response.result {
                case .success( let data):

                    completionHandler(data as? NSDictionary, nil)

                case .failure(let error):
                    print("Request failed with error: \(error)")
                    completionHandler(nil, error as NSError?)
                }
        }
        return self
    }
}

这是我序列化的代码

final public class Exercise: ResponseObjectSerializable {
    var id: Int!
    var description: String!
    var name: String!
    var muscles: String!
    var equipment: String!

    public init?(response: HTTPURLResponse, representation: Any) {

        guard
            let representation = representation as? [String: Any],
            let id = representation["id"] as? Int,
            let description = representation["description"] as? String,
            let name = representation["name"] as? String,
            let muscles = representation["muscles"] as? String,
            let equipment = representation["equipment"] as? String

        else { return nil }

        self.id = id
        self.description = description
        self.name = name
        self.muscles = muscles
        self.equipment = equipment

    }

}

但我无法解决如何将其纳入我的视图控制器函数调用,这是当前的

    let apiService = ApiService()
let searchController = UISearchController(searchResultsController: nil)

var arrRes: [String] = []
var filtered: [String] = []
var searchActive: Bool = false

var id: Int?
var description: String?
var name: String?
var muscles: String?
var equipment: String?


override func viewDidLoad() {
    super.viewDidLoad()
    exercisesTableView.delegate = self
    exercisesTableView.dataSource = self
    exerciseSearchBar.delegate = self
    getApiData()
}

func getApiData() {

    let _ = apiService.getData() {
        (data, error) in
        if let data = data {

            if let arr = data["results"] as? [String] {

                self.arrRes = arr
                self.exercisesTableView.reloadData()
            }

        } else if let error = error {
            print(error)
        }
    }
}

1 个答案:

答案 0 :(得分:1)

  • 首先,HTTP响应完全不影响自定义类,所以我把它遗漏了。
  • 密钥musclesequipment的所有值中的第二个是数组而不是字符串。
  • 第三,因为JSON数据似乎是不可变的,所以将类中的属性声明为常量(let

稍微改变一下,这就是自定义类

final public class Exercise {
   let id : Int
   let description: String
   let name: String
   let muscles : [Int]
   let equipment : [Int]

   public init?(dictionary: [String: Any]) {

      guard
         let id = dictionary["id"] as? Int,
         let description = dictionary["description"] as? String,
         let name = dictionary["name"] as? String,
         let muscles = dictionary["muscles"] as? [Int],
         let equipment = dictionary["equipment"] as? [Int]

         else { return nil }

      self.id = id
      self.description = description
      self.name = name
      self.muscles = muscles
      self.equipment = equipment
   }
}

然后你必须声明数据源数组

var exercises = [Exercise]()

在方法getApiData()中填充数组

     ...
     if let results = data["results"] as? [[String:Any]] {
        for result in results {
           if let exercise = Exercise(dictionary: result) {
              self.exercises.append(exercise)
           }
        }
        self.exercisesTableView.reloadData() // might be dispatched on the main thread.
     }

注意:Any用于Swift 3,在Swift 2中用Any替换所有AnyObject