我在使用Cloud Firestore的GeoPoint初始化商店的位置时尝试设置代码时遇到麻烦。我在尝试设置初始化程序以能够处理数据时遇到2个错误,我对问题所在的位置发表了评论。
错误显示在我的private init?(documentID: String, dictionary: [String: Any]) {
中:
'let'不能嵌套在另一个'var'或'let'模式和期望模式内
条件绑定的初始化程序必须具有可选类型,而不是“ CLLocationCoordinate2D”
我一直在尝试修改我的模型,使其代码更整洁,以便更好地处理数据,减少错误和故障,而这只是与在此结构中设置的GeoPoint费劲。
struct Stores {
var documentID: String
var name: String
var category: String
var price: Int
var imageURL: URL
var description: String
var location: CLLocationCoordinate2D
var distanceFromUser: Double
var rating: Int
// self.distanceFromUser = (CLLocationManager().location?.distance(from: CLLocation(latitude: location.latitude, longitude: location.longitude)))!
// print("look here!", self.distanceFromUser)
}
extension Stores: DocumentSerializable {
init(name: String,
category: String,
price: Int,
description: String,
rating: Int,
imageURL: URL,
location: CLLocationCoordinate2D,
distanceFromUser: Double) {
let document = Firestore.firestore().products.document()
self.init(documentID: document.documentID,
name: name,
category: category,
price: price,
imageURL: imageURL,
description: description,
location: location,
distanceFromUser: (CLLocationManager().location?.distance(from: CLLocation(latitude: location.latitude, longitude: location.longitude)))!,
rating: rating)
}
/// Initializes a stores from a documentID and some data, ostensibly from Firestore.
private init?(documentID: String, dictionary: [String: Any]) {
guard let name = dictionary["name"] as? String,
let category = dictionary["category"] as? String,
let price = dictionary["price"] as? Int,
let rating = dictionary["rating"] as? Int,
let description = dictionary["description"] as? String,
let imageURLString = dictionary["photoURL"] as? String,
//ERRORS HERE\\
let geoPoint = dictionary["location"] as? GeoPoint else { return nil}
let latitude = geoPoint.latitude,
let longitude = geoPoint.longitude, // errors: 'let' cannot appear nested inside another 'var' or 'let' pattern & Expected pattern
guard let location = CLLocationCoordinate2D(latitude: latitude, longitude: longitude) else { return nil } // error: Initializer for conditional binding must have Optional type, not 'CLLocationCoordinate2D'
// ERRORS END \
guard let imageURL = URL(string: imageURLString) else { return nil }
self.init(documentID: documentID,
name: name,
category: category,
price: price,
imageURL: imageURL,
rating: rating,
description: description,
location: location)
}
init?(document: QueryDocumentSnapshot) {
self.init(documentID: document.documentID, dictionary: document.data())
}
init?(document: DocumentSnapshot) {
guard let data = document.data() else { return nil }
self.init(documentID: document.documentID, dictionary: data)
}
/// The dictionary representation of the restaurant for uploading to Firestore.
var documentData: [String: Any] {
return [
"name": name,
"category": category,
"price": price,
"imageURL": imageURL.absoluteString,
"description": description
"rating": rating,
"location": location
]
}
}
public protocol DocumentSerializable {
init?(document: QueryDocumentSnapshot)
init?(document: DocumentSnapshot)
var documentID: String { get }
var documentData: [String: Any] { get }
}
extension Firestore {
/// Returns a reference to the top-level stores collection.
var stores: CollectionReference {
return self.collection("stores")
}
}
最佳答案
您只是忘记了以guard
结尾长的else { return nil }
表达式。
更换
let geoPoint = dictionary["location"] as? GeoPoint,
用
let geoPoint = dictionary["location"] as? GeoPoint else { return nil }
然后放置
let latitude = geoPoint.latitude
let longitude = geoPoint.longitude
在下面,您应该会很好。最后两个分配不会失败,因此您可以将它们放在
guard
语句中。