Невозможно назначить переменные функции меткам на Swift - PullRequest
0 голосов
/ 05 мая 2020

Я работаю над приложением, которое декодирует файл JSON и создает три переменные из функции: Status , emptySlots , freeBikes . Я хочу присвоить эти значения меткам. Однако, что бы я ни делал, мне не удалось получить никаких результатов ни одним методом.

Код функции:

func getBikeData(stationName:String){

    if let url = URL(string: "https://api.citybik.es//v2/networks/baksi-bisim"){
   let task = URLSession.shared.dataTask(with: url) { (data, response, error) in
           guard let dataResponse = data, error == nil else {
           print(error?.localizedDescription ?? "Response Error")
           return
       }
       do {
           //here dataResponse received from a network request
           let jsonResponse = try JSONSerialization.jsonObject(with:
                                  dataResponse, options: [])
           print(jsonResponse) //Response result


           do {
               //here dataResponse received from a network request
               let decoder = JSONDecoder()
               //Decode JSON Response Data

            let model = try decoder.decode(ResponseJSON.self, from: dataResponse)
            print(model)//Output - 1221

            if let station = model.network.stations.first(where: { $0.name == stationName }) {
            //get the properties of station here as per requirement
                let emptySlots: Int = station.empty_slots
                let freeBikes: Int = station.free_bikes
                let Status: String = station.extra.status
                print(emptySlots, freeBikes, Status)
            }

           }
           catch let parsingError {
               print("Error", parsingError)
           }

        } catch let parsingError {
           print("Error", parsingError)
        }


   }
   task.resume()

 }
}

Любая помощь приветствуется. Я уже пытался вернуть переменные, используя блок завершения.

Ответ JSON Struct:

struct ResponseJSON: Codable {
        let network: Stations
    }

Ответы [ 3 ]

1 голос
/ 05 мая 2020

Самое простое решение:

if let station = model.network.stations.first(where: { $0.name == stationName }) {
    DispatchQueue.main.async {
        self.emptySlotsLabel.text = String(station.empty_slots)
        self.freeBikesLabel.text = String(station.free_bikes)
        self.statusLabel.text = station.extra.status
    }
}

emptySlotsLabel, freeBikesLabel и statusLabel - метки, замените имена на настоящие

1 голос
/ 05 мая 2020

Один из способов решить эту проблему - использовать закрытие. Чтобы упростить задачу, создайте структуру, содержащую значения

struct BikeResponse {
    let status: String
    let freeBikes: Int
    let emptySlots: Int
}

, а затем измените объявление функции на

func getBikeData(stationName:String, completion: (BikeResponse)->(Void)){

, а затем после декодирования вы вызовете обработчик завершения

if let station = model.network.stations.first(where: { $0.name == stationName }) {
    let response = BikeResponse(status: station.extra.status,
                                freeBikes: station.free_bikes,
                                emptySlots: station.empty_slots)
    completion(response)

А затем в коде завершения вы можете присвоить значения своим меткам

getBikeData(stationName: "ABC") { response in
    DispatchQueue.main.async {
     someLabel.text = response.status
     //...
    }
}
0 голосов
/ 05 мая 2020

вам нужно добавить обработчик завершения к вашей функции. Потому что вы пытаетесь сделать asyn c запрос. После вызова getbikedata fun c вы можете присвоить значение своим меткам. Пример кода выглядит так:

func getBikeData(stationName:String, completion: @escaping (Station) -> Void) {
// ... your code here
        if let station = model.network?.stations?.first(where: { $0.name == stationName }) {
            //get the properties of station here as per requirement
            // let emptySlots: Int = station.emptySlots!
            // let freeBikes: Int = station.freeBikes!
            // let Status: String = (station.extra?.status)!.rawValue
            completion(station)
        }
// ... other your code here
}

И использование:

getBikeData(stationName: stationName) { (station) in
    print(station)
    // For example
    label.text = station.emptySlots
}
Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...