首页 > 解决方案 > Swift 中的闭包:它们是什么?他们是如何工作的?

问题描述

我正在阅读一本关于 Swift 基础知识的书,而关于闭包的部分对我来说毫无意义。

这是他们提供的示例:

要对数组进行排序以使小数排在大数之前,您可以提供一个描述如何进行排序的闭包,如下所示:

var numbers = [2,1,56,32,120,13]
// Sort so that small numbers go before large numbers

var numbersSorted = numbers.sort({
    (n1: Int, n2: Int) -> Bool in return n2 > n1
})
// = [1, 2, 13, 32, 56, 120]

我不明白在这种情况下关闭的目的是什么——numbers.sort()即使没有关闭也不会返回相同的值?另外,我不确定闭包在这里逐步执行的实际操作。

更广泛地说,我不能从这个例子中确定你何时可以在 Swift 中使用闭包。从精神上讲,它们似乎接近于减少功能,但我不确定你什么时候会使用它们。

编辑:这个代码示例在我正在使用的 Swift 游乐场(v. 12.0)中不起作用也无济于事。它抱怨调用sortMissing argument label 'by:' in call. 也许有一个更好的闭包例子。

标签: swift

解决方案


用非常简单的术语来说,闭包是一个可以传递的函数。

关于使用排序,您可以选择对对象的不同属性进行排序,因此您可能希望创建自己的自定义排序函数/闭包。

sort注意 Swift和sortedSwift之间是有区别的。sort改变原始数组,sorted创建数组的副本。所以在你的例子numbersSorted中不会有一个值,sorted如果你希望它有一个值,你应该使用它。

let numbers = [2, 5, 3, 2, 1, 0, -8, 12]

let numbersSorted = numbers.sorted { first, second -> Bool in
    return first < second
}

print(numbers)              // [2, 5, 3, 2, 1, 0, -8, 12]
print(numbersSorted)        // [-8, 0, 1, 2, 2, 3, 5, 12]

但是我不需要像那样编写上面的代码。我可以将闭包换成函数。

let numbers = [2, 5, 3, 2, 1, 0, -8, 12]

func ascending(first: Int, second: Int) -> Bool {
    first < second
}

let numbersSorted = numbers.sorted(by: ascending)

print(numbers)              // [2, 5, 3, 2, 1, 0, -8, 12]
print(numbersSorted)        // [-8, 0, 1, 2, 2, 3, 5, 12]

请注意,该函数ascending与我们之前使用的闭包具有相同的签名。

或者,我可以将闭包编写为变量,然后可以传递

let numbers = [2, 5, 3, 2, 1, 0, -8, 12]

let ascending = { (first: Int, second: Int) in 
    return first < second
}

let numbersSorted = numbers.sorted(by: ascending)

print(numbers)              // [2, 5, 3, 2, 1, 0, -8, 12]
print(numbersSorted)        // [-8, 0, 1, 2, 2, 3, 5, 12]

最重要的是函数和闭包的签名匹配。这样他们就可以互换了。

我个人更喜欢选择第二个选项,因为它使代码更具可读性并且看起来更干净。

当涉及到闭包时,您必须应对另一个术语,那就是@escaping. 这意味着什么?

@escaping闭包的寿命比它传递给的函数长。基本上是说这个代码应该在函数被调用后执行。

这在网络呼叫时很常见,因为它们可能需要一段时间才能完成。该函数将已执行但您尚未收到响应,一旦返回响应,它就会执行完成块(我们的闭包),我们可以看到更新。

这里有一些你可以跟进的好文章

https://learnappmaking.com/closures-swift-how-to/

https://www.hackingwithswift.com/example-code/language/what-is-a-closure

https://www.swiftbysundell.com/basics/closures/

https://www.hackingwithswift.com/example-code/language/what-is-an-escaping-closure


推荐阅读