【问题标题】:Unable to add json key values in array why in swift无法在数组中添加json键值为什么在swift中
【发布时间】:2019-09-30 14:30:08
【问题描述】:

我的 json 包含图像、类型和 id.. 在这里我希望我的 id 在名为 idArray 的单独数组中.. 在这里我能够在日志中获取单个 id,我已将 id 附加到 idArray 但我没有得到 id数组它显示 nil 为什么?

我已将 idArray 作为字符串。请帮我写代码。

这是我的 json 结构:

{
"financer": [
{
    "id": "45",
    "icon": "https://hello.com//images/img1.png"
     "tpe": "bank"
}
{
    "id": "40",
    "icon": "https://hello.com//images/img2.png"
     "tpe": "wallet"
 }
 .
 .
 .
]
}

这是我的代码:

import UIKit
import SDWebImage
struct JsonData {

var iconHome: String?
var typeName: String?
init(icon: String, tpe: String) {
    self.iconHome = icon
    self.typeName = tpe
}
}

class HomeViewController: UIViewController, UICollectionViewDelegate, UICollectionViewDataSource, UITextFieldDelegate {

@IBOutlet weak var collectionView: UICollectionView!
var itemsArray = [JsonData]()
var idArray = [String]()
override func viewDidLoad() {
    super.viewDidLoad()

    homeServiceCall()

}

func collectionView(_ collectionView: UICollectionView, numberOfItemsInSection section: Int) -> Int {
    return itemsArray.count
}

func collectionView(_ collectionView: UICollectionView, cellForItemAt indexPath: IndexPath) -> UICollectionViewCell {

    let cell = collectionView.dequeueReusableCell(withReuseIdentifier: "cell", for: indexPath) as! HomeCollectionViewCell

    let aData = itemsArray[indexPath.row]
    cell.paymentLabel.text = aData.typeName
    cell.paymentImage.sd_setImage(with: URL(string:aData.iconHome!), placeholderImage: UIImage(named: "GVMC_icon"))

    return cell
}

func collectionView(_ collectionView: UICollectionView, didSelectItemAt indexPath: IndexPath) {

    if let nextViewController = self.storyboard?.instantiateViewController(withIdentifier: "MakePaymentViewController") as? MakePaymentViewController
    {
        nextViewController.financerId = idArray[indexPath.row]
        self.navigationController?.pushViewController(nextViewController, animated: true)
    }
    else{
        AlertFun.ShowAlert(title: "", message: "will update soon..", in: self)
    }
}
//MARK:- Service-call

func homeServiceCall(){

    let urlStr = "https://webservices/getfinancer"
    let url = URL(string: urlStr)
    URLSession.shared.dataTask(with: url!, completionHandler: {(data, response, error) in

        guard let respData = data else {
            return
        }
        guard error == nil else {
            print("error")
            return
        }
        do{

            let jsonObj = try JSONSerialization.jsonObject(with: respData, options: .allowFragments) as! [String: Any]
            //print("the home json is \(jsonObj)")
            let financerArray = jsonObj["financer"] as! [[String: Any]]
            print("home financerData \(financerArray)")

            for financer in financerArray {

                let id = financer["id"] as? String
                let pic = financer["icon"] as? String
                let typeName = financer["tpe"] as! String
                print("home financer id \(String(describing: id))")
                self.idArray.append(id ?? "")
                print("the home financer idsArray \(self.idArray.append(id ?? ""))")

                self.itemsArray.append(JsonData(icon: pic ?? "", tpe: typeName))
            }

            DispatchQueue.main.async {
                self.collectionView.reloadData()
            }
        }
        catch {
            print("catch error")
        }

    }).resume()
}
}

无法在单独的数组中生成 json id,请在我的代码中帮助我。

【问题讨论】:

    标签: arrays json swift dictionary


    【解决方案1】:

    不要使用多个数组作为数据源。这是非常糟糕的做法。

    创建两个符合Decodable的结构

    struct Root : Decodable {
        let financer : [Financer]
    }
    
    enum Type : String, Decodable {
        case bank, wallet
    }
    
    struct Financer : Decodable {
        let id : String
        let icon : URL
        let tpe : Type
    }
    

    声明数据源数组

    var itemsArray = [Financer]()
    

    然后删除

    罢工>

    var idArray = [String]()
    

    homeServiceCall 替换为

    func homeServiceCall() {
    
        let url = URL(string: "https://dev.com/webservices/getfinancer")
        URLSession.shared.dataTask(with: url!, completionHandler: {(data, response, error) in
            if let error = error { print(error); return }
    
            do {
                DispatchQueue.main.async {
                    self.activityIndicator.startAnimating()
                }
                let result = try JSONDecoder().decode(Root.self, from:  data!)
                self.itemsArray = result.financer
                DispatchQueue.main.async {
                    self.collectionView.reloadData()
                }
            }
            catch {
                print(error) -- print always the error instance.
            }
        }).resume()
    }
    

    cellForRow 中获取id 的值

    let aData = itemsArray[indexPath.row]
    cell.paymentLabel.text = aData.id
    

    重要提示:

    永远不要使用同步 Data(contentsOf 从远程 URL 加载数据。使用一个 API,它a同步加载数据并缓存图像

    【讨论】:

    • 谢谢,但我需要单独数组中的 id,因为通过使用 idsarray,我需要在索引路径的 didselectIteam 中推送不同的视图控制器
    • 不,你不这样做,从数组中的项目中获取 id,就像在cellForRow中一样
    • 我已经删除了那个问题,我已经更新了这个问题。如果我没有单独的 id 数组,那么我如何在 didselectIteam 中推送不同的视图控制器
    • didselect 中的 financerId 用于不同的视图控制器,取决于不同的视图控制器,financerId 会改变..
    • didSelectItem 中将nextViewController.financerId = idArray[indexPath.row] 替换为nextViewController.financerId = itemsArray[indexPath.row].id。这将为选定的索引路径传递id
    猜你喜欢
    • 1970-01-01
    • 2014-10-10
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2021-04-24
    • 2018-04-13
    • 1970-01-01
    相关资源
    最近更新 更多