Swift 4中的反向地理编码

我正在尝试编写一个简单的方法,该方法已馈入CLLocationDegrees并返回CLPlacemark。查看Apple的文档,这似乎很简单。

以下是我丢到操场上的东西:

import CoreLocation

// this is necessary for async code in a playground

import PlaygroundSupport

// this is necessary for async code in a playground

PlaygroundPage.current.needsIndefiniteExecution = true

func geocode(latitude: CLLocationDegrees, longitude: CLLocationDegrees) -> CLPlacemark? {

let location = CLLocation(latitude: latitude, longitude: longitude)

let geocoder = CLGeocoder()

var placemark: CLPlacemark?

geocoder.reverseGeocodeLocation(location) { (placemarks, error) in

if error != nil {

print("something went horribly wrong")

}

if let placemarks = placemarks {

placemark = placemarks.first

}

}

return placemark

}

let myPlacemark = geocode(latitude: 37.3318, longitude: 122.0312)

就目前而言,我的方法返回nil。我不确定我的错误在哪里,但是我可以放心,这对我来说是愚蠢的。感谢您的阅读。

回答:

import UIKit

import CoreLocation

import PlaygroundSupport

PlaygroundPage.current.needsIndefiniteExecution = true


func geocode(latitude: Double, longitude: Double, completion: @escaping (_ placemark: [CLPlacemark]?, _ error: Error?) -> Void)  {

CLGeocoder().reverseGeocodeLocation(CLLocation(latitude: latitude, longitude: longitude)) { placemark, error in

guard let placemark = placemark, error == nil else {

completion(nil, error)

return

}

completion(placemark, nil)

}

}

或者简单地:

func geocode(latitude: Double, longitude: Double, completion: @escaping (_ placemark: [CLPlacemark]?, _ error: Error?) -> Void)  {

CLGeocoder().reverseGeocodeLocation(CLLocation(latitude: latitude, longitude: longitude), completionHandler: completion)

}

或扩展CLLocation:

extension CLLocation {

func geocode(completion: @escaping (_ placemark: [CLPlacemark]?, _ error: Error?) -> Void) {

CLGeocoder().reverseGeocodeLocation(self, completionHandler: completion)

}

}


要将地标格式化为邮寄地址,可以使用“联系人”框架CNPostalAddressFormatter

import Contacts

extension Formatter {

static let mailingAddress: CNPostalAddressFormatter = {

let formatter = CNPostalAddressFormatter()

formatter.style = .mailingAddress

return formatter

}()

}

extension CLPlacemark {

var mailingAddress: String? {

return postalAddress?.mailingAddress

}

}

extension CNPostalAddress {

var mailingAddress: String {

return Formatter.mailingAddress.string(from: self)

}

}


包含CLPlacemark对象的数组。对于大多数地理编码请求,此数组应仅包含一个条目。但是,在无法将指定地址解析到单个位置的情况下,前向地理编码请求可能会返回多个地标对象。如果请求被取消或获取地标信息时出错,则此参数为nil。

有关CLPlacemark属性的更多信息,可以检查此CLPlacemark


用法:

let location = CLLocation(latitude: -22.963451, longitude: -43.198242)

location.geocode { placemark, error in

if let error = error as? CLError {

print("CLError:", error)

return

} else if let placemark = placemark?.first {

// you should always update your UI in the main thread

DispatchQueue.main.async {

// update UI here

print("name:", placemark.name ?? "unknown")

print("address1:", placemark.thoroughfare ?? "unknown")

print("address2:", placemark.subThoroughfare ?? "unknown")

print("neighborhood:", placemark.subLocality ?? "unknown")

print("city:", placemark.locality ?? "unknown")

print("state:", placemark.administrativeArea ?? "unknown")

print("subAdministrativeArea:", placemark.subAdministrativeArea ?? "unknown")

print("zip code:", placemark.postalCode ?? "unknown")

print("country:", placemark.country ?? "unknown", terminator: "\n\n")

print("isoCountryCode:", placemark.isoCountryCode ?? "unknown")

print("region identifier:", placemark.region?.identifier ?? "unknown")

print("timezone:", placemark.timeZone ?? "unknown", terminator:"\n\n")

// Mailind Address

print(placemark.mailingAddress ?? "unknown")

}

}

}


这将打印

name: Morro da Saudade

address1: Rua Casuarina

address2: 597

neighborhood: Lagoa

city: Rio de Janeiro

state: RJ

subAdministrativeArea: unknown

zip code: 22011-040

country: Brazil

isoCountryCode: BR

region identifier: <-22.96345100,-43.19824200> radius 141.83

timezone: America/Sao_Paulo (current)

Rua Casuarina,597

拉哥亚

里约热内卢

22011-040

巴西

以上是 Swift 4中的反向地理编码 的全部内容, 来源链接: utcz.com/qa/399082.html

回到顶部