我正在尝试创建一个功能,以在应用加载时检查连通性。如果检测到互联网连接,则该应用程序应下载JSON数据并将该数组保存在UserDefaults中,然后继续执行UITableView方法。但是,如果找不到互联网连接,则应用程序应在USerDefault上恢复该数组以填充另一个数组,然后继续执行UItableView方法。
我面临的问题是,当编译器通过UserDefault行以能够保存数组时,应用程序立即崩溃。我在做什么错了?
编译器错误:
)进行密钥备份已保存' ***第一个抛出调用堆栈:(0x18257ad8c 0x1817345ec 0x18257ac6c 0x1825b1d08 0x1824e730c 0x1824e5a60 0x1825b2080 0x182515cec 0x1825b2080 0x1825b2304 0x182518d6c 0x182518588 0x182518c54 0x1825bc218 0x1825bf8a0 0x182edaaf4 0x102a794c0 0x102a7452c 0x102e8d314 0x102e45b7c 0x103da11dc 0x103da119c 0x103da5d2c 0x182523070 0x182520bc8 0x182440da8 0x184425020 0x18c45d758 0x102a756b0 0x181ed1fc0)libc ++ abi.dylib:未捕获终止 NSException(lldb)类型的异常
[FIXED] ViewController:
import UIKit
import Kingfisher
import Alamofire
var arrCerveja = [Cerveja]()
var arrBackup = [Cerveja]()
class ViewController: UIViewController, UITableViewDelegate, UITableViewDataSource {
@IBOutlet weak var tableView: UITableView!
//TableView DataSource
func tableView(_ tableView: UITableView, numberOfRowsInSection section: Int) -> Int {
if Connectivity.isConnectedToInternet {
return arrCerveja.count
} else {
return arrBackup.count
}
}
func tableView(_ tableView: UITableView, cellForRowAt indexPath: IndexPath) -> UITableViewCell {
let cell = tableView.dequeueReusableCell(withIdentifier: "cellID") as! TableViewCell
if Connectivity.isConnectedToInternet {
let model = arrCerveja[indexPath.row]
cell.labelName.text = model.name
cell.labelDetail.text = "Teor alcoólico: \(model.abv)"
let resource = ImageResource(downloadURL: URL(string: "\(model.image_url)")!, cacheKey: model.image_url)
cell.imageViewCell.kf.setImage(with: resource, placeholder: UIImage(named: "icons8-hourglass-48"), options: nil, progressBlock: nil, completionHandler: nil)
return cell
} else {
let model = arrBackup[indexPath.row]
cell.labelName.text = model.name
cell.labelDetail.text = "Teor alcoólico: \(model.abv)"
let resource = ImageResource(downloadURL: URL(string: "\(model.image_url)")!, cacheKey: model.image_url)
cell.imageViewCell.kf.setImage(with: resource, placeholder: UIImage(named: "icons8-hourglass-48"), options: nil, progressBlock: nil, completionHandler: nil)
return cell
}
}
//TableView Delegate
func tableView(_ tableView: UITableView, didSelectRowAt indexPath: IndexPath) {
if Connectivity.isConnectedToInternet {
performSegue(withIdentifier: "segueId", sender:arrCerveja[indexPath.row])
} else {
performSegue(withIdentifier: "segueId", sender:arrBackup[indexPath.row])
}
}
override func prepare(for segue: UIStoryboardSegue, sender: Any?) {
if segue.identifier == "segueId" {
let des = segue.destination as? TableViewDetalhes
//.item possui uma propriedade instanciada na TelaDetalheProdutos
des?.item = (sender as? Cerveja)
//Segue para CollectionView Categorias
}
}
struct Connectivity {
static let sharedInstance = NetworkReachabilityManager()!
static var isConnectedToInternet:Bool {
return self.sharedInstance.isReachable
}
}
override func viewDidAppear(_ animated: Bool) {
if Connectivity.isConnectedToInternet {
print("Connected")
getApiData { (cerveja) in
arrCerveja = cerveja
//Backup
do{
let data = try JSONEncoder().encode(arrCerveja)
UserDefaults.standard.set(data, forKey: "backupSaved")
//
self.tableView.reloadData()
}catch{print(error)
}
}
} else {
print("No Internet")
do{
if let savedData = UserDefaults.standard.value(forKey: "backupSaved") as? Data {
arrBackup = try JSONDecoder().decode([Cerveja].self, from: savedData)
self.tableView.reloadData()
}
}catch{
print(error)
}
}
}
override func viewDidLoad() {
super.viewDidLoad()
//SetupNavBarCustom
navigationController?.navigationBar.setupNavigationBar()
}
}
型号:
struct Cerveja:Decodable{
let name:String
let image_url:String
let description:String
let tagline:String
let abv:Double
let ibu:Double?
}
答案 0 :(得分:1)
在保存之前,应将数组末尾编码为Data,因为它是自定义对象的数组
do {
....... write
let data = try JSONEncoder().encode(arr)
UserDefaults.standard.set(data, forKey: "backupSaved")
// save as data
....... read
if let savedData = UserDefaults.standard.value(forKey: "backupSaved") as? Data {
let savedArr = try JSONDecoder().decode([Cerveja].self, from: savedData)
// use the array here
}
}
catch {
print(error)
}
//
从现在开始您进行编码和解码
struct Cerveja:Codable {--}
//
我也不赞成保存在userDefaults中,请考虑使用CoreData