[英]When to use equal sign after declare a variable with closure in Swift
我刚刚看到了Apple的示例代码:
let timeRemainingFormatter: NSDateComponentsFormatter = {
let formatter = NSDateComponentsFormatter()
formatter.zeroFormattingBehavior = .Pad
formatter.allowedUnits = [.Minute, .Second]
return formatter
}()
var timeRemainingString: String {
let components = NSDateComponents()
components.second = Int(max(0.0, timeRemaining))
return timeRemainingFormatter.stringFromDateComponents(components)!
}
问题是:常量和变量都用闭包声明,但是一个带有等号,另一个则没有。 为什么?
()
说“立即执行并返回结果”。 现在来一个长篇大论的答案:
let timeRemainingFormatter: NSDateComponentsFormatter = {
// ...
}() // <- The '()' means "execute now and give me the formatter"
在初始化时间, timeRemainingFormatter
将被计算一次 ,并且该值将被存储。 括号表示应立即执行闭包并返回结果,在这种情况下,应将其存储为属性。
var timeRemainingString: String {
// ...
}
timeRemainingString
将在每次调用时进行计算。
更一般而言,在Swift中,函数仅被称为闭包。 定义一个类似的函数:
func myFunc() -> Void {
print("Function")
}
与定义闭包几乎相同:
let myClosure: () -> Void = {
print("Closure")
}
在这两种情况下,您都有一个名称( myFunc
/ myClosure
),一个呼叫签名( () -> Void
)和一个代码块( { print(...) }
)。
就像调用函数一样:
myFunc()
您可以将存储的闭包称为:
myClosure()
并且都将打印。
函数几乎只是定义命名闭包的一种便利。
假设您有一个全局函数和一个全局存储的闭包,分别定义为:
func myIntFunc() -> Int { return 1 }
let myIntClosure: () -> Int = { return 2 }
相似之处应该很明显。
现在,您想在类中将它们用作属性。 你会的
class MyClass {
let funcInt: Int = myIntFunc() // would resolve to 1
let closureInt: Int = myIntClosure() // would resolve to 2
}
请注意,两者的结尾都有()
。 那就是“执行我的函数/闭包以立即获取Int
。”
现在,假设您不想定义全局闭包; 您宁愿将该代码放在您的课程中,以使事情井井有条。 所以你也是:
class MyClass {
let funcInt: Int = myIntFunc() // would resolve to 1
let closureInt: Int = { return 2 }() // would resolve to 2
}
就像函数一样,您仍然需要执行闭包才能将Int
移出闭包。 因此,就像函数一样,将()
放在其后。
最后,我们将涉及“计算的属性”。
var timeRemainingString: String {
// ...
}
您可以将其视为编写不带任何参数的函数的一种方式,从而获得快捷调用签名(可以将其视为属性)。 确实就像闭包是由属性存储的,但是因为它是一种特殊的表示法,所以Swift知道执行闭包并在每次调用该属性时返回其结果。 因此,这是“计算的属性”。
你打电话时:
let timeRemaining = instance.timeRemainingString
Swift确实将其翻译为:
let timeRemaining = instance.timeRemainingString()
只需添加()
即可使存储的闭包执行。
实际上,事情要复杂得多,因为您可以定义setter闭包以及刚刚讨论的getter,甚至还可以定义观察者闭包。 Swift会根据您要执行的操作类型将其分派到正确的闭包。
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.