Swift - 在闭包中计算不可变对象效率低吗?
Swift - is it inefficient to calculate an immutable within a closure?
我喜欢案例 2,因为它将相关代码放在一个地方,但是如果我这样做,每次计算闭包时常量都会重新计算吗?
let numCols = 99
// case 1
let spacing = (width - margin.left - margin.right) / (numCols - 1)
let xCoord = { (Int: col) -> Float in margin.left + col * spacing }
// case 2
let xCoord = { (Int: col) -> Float in
let spacing = (width - margin.left - margin.right) / (numCols - 1)
return margin.left + col * spacing
}
简短的回答是肯定的,在闭包中计算不可变是低效的。
原因如下。假设您有这样的代码:
let numCols = 99.0
let width = 800.0
let marginLeft = 15.0
let marginRight = 20.0
// case 1
let spacing: Double = (width - marginLeft - marginRight) / (numCols - 1)
let xCoord1 = { (col: Double) -> Double in
return marginLeft + col * spacing
}
// case 2
let xCoord2 = { (col: Double) -> Double in
let spacing: Double = (width - marginLeft - marginRight) / (numCols - 1)
return marginLeft + col * spacing
}
这些是您示例中的情况 1 和情况 2,稍作修改以在 Playground 中编译。
让我们做一个简单的 for 循环来测量这些函数每个执行 2500 次:
let startTime = CACurrentMediaTime()
for var i in 0...2500
{
xCoord1(10)
}
let totalTime = CACurrentMediaTime() - startTime
print("time: - \(totalTime) sec")
案例 1 在我的机器上执行时间为 0.99 秒(如果您的硬件特性较低或较高,可能会有所不同)。
现在,让我们看看如果对案例 2 执行相同操作会得到什么:
let startTime2 = CACurrentMediaTime()
for var i in 0...2500
{
xCoord2(10)
}
let totalTime2 = CACurrentMediaTime() - startTime2
print("time: - \(totalTime2) sec")
案例 2 在我的机器上执行时间为 1.49 秒,这意味着它的效率低于案例 1。
因此,如果您的宽度、边距和列数不变,最好计算一次间距并将其存储在常量中。
但是,如果您不必多次重复此计算而只需要一次,您仍然可以将其保留在闭包中以提高可读性。
在您的环境中使用衡量性能的代码,看看您是否失去了性能,并据此做出决定。
我喜欢案例 2,因为它将相关代码放在一个地方,但是如果我这样做,每次计算闭包时常量都会重新计算吗?
let numCols = 99
// case 1
let spacing = (width - margin.left - margin.right) / (numCols - 1)
let xCoord = { (Int: col) -> Float in margin.left + col * spacing }
// case 2
let xCoord = { (Int: col) -> Float in
let spacing = (width - margin.left - margin.right) / (numCols - 1)
return margin.left + col * spacing
}
简短的回答是肯定的,在闭包中计算不可变是低效的。
原因如下。假设您有这样的代码:
let numCols = 99.0
let width = 800.0
let marginLeft = 15.0
let marginRight = 20.0
// case 1
let spacing: Double = (width - marginLeft - marginRight) / (numCols - 1)
let xCoord1 = { (col: Double) -> Double in
return marginLeft + col * spacing
}
// case 2
let xCoord2 = { (col: Double) -> Double in
let spacing: Double = (width - marginLeft - marginRight) / (numCols - 1)
return marginLeft + col * spacing
}
这些是您示例中的情况 1 和情况 2,稍作修改以在 Playground 中编译。
让我们做一个简单的 for 循环来测量这些函数每个执行 2500 次:
let startTime = CACurrentMediaTime()
for var i in 0...2500
{
xCoord1(10)
}
let totalTime = CACurrentMediaTime() - startTime
print("time: - \(totalTime) sec")
案例 1 在我的机器上执行时间为 0.99 秒(如果您的硬件特性较低或较高,可能会有所不同)。
现在,让我们看看如果对案例 2 执行相同操作会得到什么:
let startTime2 = CACurrentMediaTime()
for var i in 0...2500
{
xCoord2(10)
}
let totalTime2 = CACurrentMediaTime() - startTime2
print("time: - \(totalTime2) sec")
案例 2 在我的机器上执行时间为 1.49 秒,这意味着它的效率低于案例 1。
因此,如果您的宽度、边距和列数不变,最好计算一次间距并将其存储在常量中。 但是,如果您不必多次重复此计算而只需要一次,您仍然可以将其保留在闭包中以提高可读性。 在您的环境中使用衡量性能的代码,看看您是否失去了性能,并据此做出决定。