首页 > 解决方案 > 在闭包外部声明的 Swift 变量在闭包内部更新,但是当在闭包外部访问时它返回默认值?

问题描述

所以我正在调用一个应该只返回输入地址的经度的函数。我将它附加在这里,以便您查看它,然后我将在代码之后对其进行评论:

func getLongitude(address: String) -> Double {
    var longitude: Double = 0.0
    let geocoder = CLGeocoder()
    geocoder.geocodeAddressString(address) {
        placemarks, error in 
        let placemark = placemarks?.first
        longitude = placemark?.location?.coordinate.longitude ?? 0.0
        print("The testing longitude is \(longitude)")
    }
    return longitude
}

如您所见,我将经度变量声明为默认值 0.0。在函数内部的闭包中,我更新了经度。print 语句确认在该函数的闭包中更新了经度。当在此闭包之外使用 return 语句访问经度时,它会再次返回 0.0 (我相信经度的值在闭包之外没有发生变化,但我不知道如何解决这个问题)。任何帮助将非常感激!

标签: swiftclosuresgeocode

解决方案


请使用制表符使您的代码更易于阅读。

无论如何geocoder.geocodeAddressString(address)是一个带有回调的方法,在这个回调方法中你有地标。您的返回不会等待该回调,因为计算坐标需要时间,因此它返回您在开始时设置的 0.0。


编辑:自您在评论中询问以来的更长版本:

CLGeocoder()的函数geocodeAddressString实际上有 2 个参数:地址和所谓的回调。回调只是任务(在本例中是计算地标)完成时调用的方法。Swift 允许你用“swifty”语法编写回调,但实际上它看起来像

geocoder.geocodeAddressString(address, callAfterFinishGeocoding)

func callAfterFinishGeocoding(_ placemark: Placemark) {
   // do stuff with placemark
}

如您所见,我们将地理编码函数传递给完成后要调用的另一个函数。的参数在callAfterFinishGeocoding中定义geocodeAddressString。它看起来类似于:

callback: @escaping (_ placeMark: Placemark) -> Void

这意味着回调应该是一个接受地标并返回 Void 的函数。跳转到方法的定义,看看它想要什么样的函数作为参数。

还可以在这里阅读更多内容:https ://stackoverflow.com/a/46245943/13087977


推荐阅读