带闭包的默认 属性 值使编译器重新编译所有文件
Default property value with closure makes a compiler to recompile all files
这个 source 有一个段落 Setting a Default 属性 Value with a Closure or Function 我们可以在其中找到一个例子
Here’s a skeleton outline of how a closure can be used to provide a default property value:
class SomeClass {
let someProperty: SomeType = {
// create a default value for someProperty inside this closure
// someValue must be of the same type as SomeType
return someValue
}()
}
好吧,我经常使用它...另外,我经常在只更改一个符号后等待整个项目重新编译。而今天我发现这两个东西是相互关联的。
假设我们有一些class,我们在其中设置一些带有闭包和函数的默认属性
class Class1 {
let value: Int
init(_ value: Int) {
self.value = value
}
private lazy var lazyValueWithClosure: Int = {
return 1111
}()
private lazy var lazyValueWithFunction: Int = self.getValue()
private func getValue() -> Int {
return 2222
}
}
我们还有一些其他的 class 在一个单独的文件中,我们使用上面的 Class1
class Class2 {
let value: Int
init(_ value: Int) {
self.value = value
_ = Class1(100)
}
}
和其他一些 class 在我们使用 Class2
的单独文件中
class Class3 {
let value: Int
init(_ value: Int) {
self.value = value
_ = Class2(100)
}
}
等等...
我决定使用 terminal
+ xcodebuild
+ grep
来仅获取有关重新编译文件的信息。这是我用来获取编译信息的命令:
xcodebuild -scheme Test -sdk iphonesimulator -arch x86_64 -configuration Debug build OTHER_SWIFT_FLAGS="-Xfrontend -debug-time-function-bodies" | grep '^[0-9]\{1,20\}.[0-9]\{1,20\}ms.*init(_ value: Int)'
准备工作到此为止。现在我们转到 Class1
并将 2222
更改为其他值。 运行以上命令并得到结果。
0.1ms /Users/iwheelbuy/Documents/recompile/Test/Classes/Class1.swift:11:5 init(_ value: Int)
效果不错。使用函数设置默认值按预期工作。我们改了一个文件,只编译了一个文件。
然后让我们将值 1111
从 Class1
更改为其他值和 运行 命令。终端输出现在看起来像这样:
0.8ms /Users/iwheelbuy/Documents/recompile/Test/Classes/Class5.swift:11:5 init(_ value: Int)
0.3ms /Users/iwheelbuy/Documents/recompile/Test/Classes/Class1.swift:11:5 init(_ value: Int)
1.0ms /Users/iwheelbuy/Documents/recompile/Test/Classes/Class4.swift:11:5 init(_ value: Int)
0.3ms /Users/iwheelbuy/Documents/recompile/Test/Classes/Class3.swift:11:5 init(_ value: Int)
0.3ms /Users/iwheelbuy/Documents/recompile/Test/Classes/Class2.swift:11:5 init(_ value: Int)
所有 classes 都被重新编译...现在假设您有一个大型项目,默认值闭包中的任何小更改都会让您等待整个项目重新编译。
问题:
- 这是什么原因?
- 关于如何使用默认值闭包而不遭受重新编译的任何建议?
- 与this topic相关?
这是 Swift 编译器中的一个已知问题。问题是一旦你像这样使用闭包或惰性属性,每个 Swift 文件都将被类型检查。我写了一篇关于这个主题的博客 post,您可以找到 here。
这个 source 有一个段落 Setting a Default 属性 Value with a Closure or Function 我们可以在其中找到一个例子
Here’s a skeleton outline of how a closure can be used to provide a default property value:
class SomeClass { let someProperty: SomeType = { // create a default value for someProperty inside this closure // someValue must be of the same type as SomeType return someValue }() }
好吧,我经常使用它...另外,我经常在只更改一个符号后等待整个项目重新编译。而今天我发现这两个东西是相互关联的。
假设我们有一些class,我们在其中设置一些带有闭包和函数的默认属性
class Class1 {
let value: Int
init(_ value: Int) {
self.value = value
}
private lazy var lazyValueWithClosure: Int = {
return 1111
}()
private lazy var lazyValueWithFunction: Int = self.getValue()
private func getValue() -> Int {
return 2222
}
}
我们还有一些其他的 class 在一个单独的文件中,我们使用上面的 Class1
class Class2 {
let value: Int
init(_ value: Int) {
self.value = value
_ = Class1(100)
}
}
和其他一些 class 在我们使用 Class2
class Class3 {
let value: Int
init(_ value: Int) {
self.value = value
_ = Class2(100)
}
}
等等...
我决定使用 terminal
+ xcodebuild
+ grep
来仅获取有关重新编译文件的信息。这是我用来获取编译信息的命令:
xcodebuild -scheme Test -sdk iphonesimulator -arch x86_64 -configuration Debug build OTHER_SWIFT_FLAGS="-Xfrontend -debug-time-function-bodies" | grep '^[0-9]\{1,20\}.[0-9]\{1,20\}ms.*init(_ value: Int)'
准备工作到此为止。现在我们转到 Class1
并将 2222
更改为其他值。 运行以上命令并得到结果。
0.1ms /Users/iwheelbuy/Documents/recompile/Test/Classes/Class1.swift:11:5 init(_ value: Int)
效果不错。使用函数设置默认值按预期工作。我们改了一个文件,只编译了一个文件。
然后让我们将值 1111
从 Class1
更改为其他值和 运行 命令。终端输出现在看起来像这样:
0.8ms /Users/iwheelbuy/Documents/recompile/Test/Classes/Class5.swift:11:5 init(_ value: Int)
0.3ms /Users/iwheelbuy/Documents/recompile/Test/Classes/Class1.swift:11:5 init(_ value: Int)
1.0ms /Users/iwheelbuy/Documents/recompile/Test/Classes/Class4.swift:11:5 init(_ value: Int)
0.3ms /Users/iwheelbuy/Documents/recompile/Test/Classes/Class3.swift:11:5 init(_ value: Int)
0.3ms /Users/iwheelbuy/Documents/recompile/Test/Classes/Class2.swift:11:5 init(_ value: Int)
所有 classes 都被重新编译...现在假设您有一个大型项目,默认值闭包中的任何小更改都会让您等待整个项目重新编译。
问题:
- 这是什么原因?
- 关于如何使用默认值闭包而不遭受重新编译的任何建议?
- 与this topic相关?
这是 Swift 编译器中的一个已知问题。问题是一旦你像这样使用闭包或惰性属性,每个 Swift 文件都将被类型检查。我写了一篇关于这个主题的博客 post,您可以找到 here。