У меня есть этот код, который я хочу загрузить некоторые данные из FirebaseDatase
func fetchVinylsData(){
SVProgressHUD.show()
guard let currentUID = Auth.auth().currentUser?.uid else { return }
dbRef.child("vinyls").child(currentUID).observe(.childAdded) { (snapshot) in
guard let dictionary = snapshot.value as? Dictionary<String,AnyObject> else { return }
let vinyl = Vinyl(dictionary: dictionary)
print(dictionary)
self.vinyls = [Vinyl]()
self.vinyls.append(vinyl)
self.vinyls.sort(by: { (vinyl1, vinyl2) -> Bool in
return vinyl1.artist < vinyl2.artist
})
self.tableView.reloadData()
}
SVProgressHUD.dismiss()
}
когда я печатаю словарь, я получаю все записи в порядке, но моя таблица не заполняется. Я работал нормально, пока не решил добавить новое поле в Vinyl.swift. Структура в базе данных firebase без нового поля. Это проблема? Вот код для Vinyl.swift:
import UIKit
import Firebase
class Vinyl {
var vinylID : String!
var title : String!
var artist : String!
var label : String!
var vinylCountry : String!
var isOut : Bool = false
var vinylLocation : String!
var year : String!
var vinylAutoID : String!
var vinylFormat : String!
init(dictionary : Dictionary<String,AnyObject>) {
guard let title = dictionary["title"] as? String else { return }
guard let artist = dictionary["artist"] as? String else { return }
guard let label = dictionary["label"] as? String else { return }
guard let vinylID = dictionary["vinylID"] as? String else { return }
guard let vinylCountry = dictionary["vinylCountry"] as? String else { return }
guard let vinylLocation = dictionary["vinylLocation"] as? String else { return }
guard let year = dictionary["vinylYear"] as? String else { return }
guard let autoID = dictionary["autoID"] as? String else { return }
guard let isOut = dictionary["isOut"] as? Bool else { return }
guard let vinylFormat = dictionary["format"] as? String else { return }
self.vinylID = vinylID
self.title = title
self.artist = artist
self.label = label
self.vinylCountry = vinylCountry
self.isOut = isOut
self.vinylLocation = vinylLocation
self.year = year
self.vinylAutoID = autoID
self.vinylFormat = vinylFormat
}
}
Я не думаю, что .init должен вернуться в любом случае. Если бы все это было условно, я бы сказал, что if let
— гораздо лучший вариант для init
.
Я бы не советовал использовать guard let
в вашем методе init
, потому что предположим, что dictionary["title"]
пуст или недоступен, тогда он вернется из первой строки вашего кода, и то же самое произойдет для других. И чтобы решить эту проблему, вы можете использовать Nil-Coalescing Operator
(означает, что вы можете назначить значение по умолчанию nil
или любое другое значение, если something["something"]
равно nil
или optional
)
Заменять
guard let title = dictionary["title"] as? String else { return }
guard let artist = dictionary["artist"] as? String else { return }
guard let label = dictionary["label"] as? String else { return }
guard let vinylID = dictionary["vinylID"] as? String else { return }
guard let vinylCountry = dictionary["vinylCountry"] as? String else { return }
guard let vinylLocation = dictionary["vinylLocation"] as? String else { return }
guard let year = dictionary["vinylYear"] as? String else { return }
guard let autoID = dictionary["autoID"] as? String else { return }
guard let isOut = dictionary["isOut"] as? Bool else { return }
guard let vinylFormat = dictionary["format"] as? String else { return }
с участием
let title = dictionary["title"] as? String ?? ""
let artist = dictionary["artist"] as? String ?? ""
let label = dictionary["label"] as? String ?? ""
let vinylID = dictionary["vinylID"] as? String ?? ""
let vinylCountry = dictionary["vinylCountry"] as? String ?? ""
let vinylLocation = dictionary["vinylLocation"] as? String ?? ""
let year = dictionary["vinylYear"] as? String ?? ""
let autoID = dictionary["autoID"] as? String ?? ""
let isOut = dictionary["isOut"] as? Bool ?? false
let vinylFormat = dictionary["format"] as? String ?? ""
И вам также необходимо обновить UI
в основной очереди, когда вы работаете с async
вызовами, как показано ниже:
DispatchQueue.main.async {
self.tableView.reloadData()
}
Я внес изменения, но теперь он вносит только одну из 20 записей в мою базу данных Firebase. Если я печатаю словарь, он показывает все записи.
может быть проблема с приведением типов. можешь показать свой словарь?
охранять словарь let = snapshot.value как? Словарь<String,AnyObject> иначе { return }
если я распечатаю свой массив виниловых пластинок .count после того, как я его извлек, я получаю 0, даже если я получаю одну строку в своем табличном представлении ... странно
Да, если это одно из свойств, которое вы читаете с помощью
guard
в своем методе инициализации, поскольку тогда новое свойство не будет частью словаря, аinit
просто вернется, по крайней мере, это моя теория. Установите для свойства, отсутствующего в базе данных, значение по умолчанию вместо использования защиты вinit
. Очень странный способ написать метод инициализации, должен сказать при всем этомreturn