我有将近 4 年的 Objective C 经验,并且是 swift 的新手。我试图从 Objective C 的角度理解 swift 的概念。所以如果我错了,请指导我:)
在目标 c 中,我们有块(可以稍后异步执行的代码块),这绝对是完全合理的。但现在在 swift 中,我们可以将一个函数作为参数传递给另一个函数,该函数可以稍后执行,然后我们也有闭包。
As per Apple “函数是子句的特殊情况。”
As per O'Reilly “当函数作为值传递时,它会携带对外部变量的内部引用。这就是函数成为闭包的原因。”
所以我尝试了一下去理解同样的事情:)
这是我的结束语
override func viewDidLoad() {
super.viewDidLoad()
// Do any additional setup after loading the view, typically from a ni
let tempNumber : Int = 5
let numbers = [1,2,3,4,5]
print (numbers.map({ $0 - tempNumber}))
}
变量 tempNumber 甚至在声明闭包之前就已声明,但闭包可以访问该变量。现在,我尝试使用传递闭包作为参数的自定义类,并尝试执行相同的代码,而不是地图:)虽然现在闭包在不同的范围内执行,但它仍然可以访问 tempNumber。
我的结论是:闭包可以访问与闭包本身在同一范围内声明的变量和方法,尽管它是在不同的范围内执行的。
现在不再将闭包作为参数传递,而是尝试将函数作为参数传递,
class test {
func testFunctionAsParameter(testMethod : (Int) -> Int){
let seconds = 4.0
let delay = seconds * Double(NSEC_PER_SEC) // nanoseconds per seconds
let dispatchTime = dispatch_time(DISPATCH_TIME_NOW, Int64(delay))
dispatch_after(dispatchTime, dispatch_get_main_queue(), {
self.callLater(testMethod)
})
}
func callLater(testMethod : (Int) -> Int) -> Int {
return testMethod(100)
}
}
在另一个类中,我创建了一个 Test 实例并按如下方式使用它
/* in differrent class */
override func viewDidLoad() {
super.viewDidLoad()
// Do any additional setup after loading the view, typically from a ni
let tempAge : Int = 5
func test2(val : Int) -> Int {
return val - tempAge;
}
let testObj = test();
print(testObj.testFunctionAsParameter(test2))
}
声明了一个名为 test 的类,该类有一个名为 testFunctionAsParameter 的方法,该方法又调用另一个名为 callLater 的方法,最后该方法执行传递的函数:)
现在所有这些马戏团,只是为了确保传递的方法在不同的范围内执行:)
当我执行上面的代码时:)我震惊地发现,即使作为参数传递的函数最终在不同的作用域中执行,仍然可以访问在与方法声明相同的作用域中声明的变量 testNumber :)
我的结论是:O'Reilly 的说法“当函数作为值传递时,它会携带对外部变量的内部引用。”很受欢迎:)
现在我的疑问是苹果说函数是子句的特殊情况。我认为特殊情况一定与作用域有关:)但令我惊讶的是代码显示闭包和函数都可以访问外部作用域中的变量!!!!
除此之外,语法差异闭包与作为参数传递的函数有何不同???现在内部肯定有一些差异,否则Apple不会花那么多时间来设计它:)
如果没有范围??那么闭包和功能还有什么不同? O'Reilly 指出“当函数作为值传递时,它会携带对外部变量的内部引用。这就是函数成为闭包的原因。”那么它想指出什么呢?该闭包不会引用外部变量?现在他们也不会错了,不是吗?
我对 Apple 和 O'Reilly 的两个相互矛盾的声明感到生气:( 请帮忙,我理解有问题吗??请帮助我理解其中的区别。