在Kotlin中,您可以使用if语句,类似于三元运算符。
我们可以选择执行以下操作:
val x = if (isOdd) 1 else 2
但是如果我们需要根据某个条件设置多个变量,那么像这样的老式方法是否更正确:
val x: Int
val y: Int
val z: Int
if (isOdd) {
x = 1
y = 3
z = 5
} else {
x = 2
y = 4
z = 6
}
或这样:
val x = if (isOdd) 1 else 2
val y = if (isOdd) 3 else 4
val z = if (isOdd) 5 else 6
第二种方法对我来说看起来更干净,但是我想知道第一种方法是否可以更快地使用计算机,因为它只需要计算一次条件,而第二种方法则需要检查条件3次。
第二种方法是真的变慢了还是会被编译器优化?
答案 0 :(得分:2)
我更喜欢这样的东西,看起来更像Kotlinesque:
data class Point3D(val x: Int, val y: Int, val z: Int)
fun foo(isOdd: Boolean): Point3D = if (isOdd) Point3D(1, 3, 5) else Point3D(2, 4, 6)
//or using destructureing see https://kotlinlang.org/docs/reference/multi-declarations.html)
val (x,y,z) = if (isOdd) Triple(1, 3, 5) else Triple(2, 4, 6)
它还结合了两者的优点,使用if
作为表达式,只需要一个if
。 (以额外的对象分配为代价)。
但是要回答您的问题。做自己喜欢的事,认为最易读。性能方面,我怀疑您会有所作为。
答案 1 :(得分:0)
if
是Kotlin中的一个表达式,而不是语句:它返回一个值,而在Java中则不是。
老实说,我认为这不是您应该考虑的优化问题。过早的优化是问题的常见根源。如果此布尔变量是线程限定的,那么我认为编译器将执行在这种情况下可能的所有优化,因此几乎完全没有开销(如果不是完全的话)。
OO语言中的明智选择是优先考虑透明性和灵活性,而不是低级优化问题(尤其是当编译器能够解决它们时)。
答案 2 :(得分:0)
好的,所以刚刚再次看到这个问题并感到好奇......所以我做了一些测试。
事实证明实际上存在巨大差异,结果如下:
代码
fun main() {
for (i in 0 until 3) {
val t1_s = System.currentTimeMillis()
for (j in 0 until 100000) {
when (i){
0 -> a(j % 2 == 0)
1 -> b(j % 2 == 0)
2 -> c(j % 2 == 0)
}
}
val t1_e = System.currentTimeMillis()
println("Test $i - time ${t1_e - t1_s}")
}
}
fun a(isOdd: Boolean): Int {
val x: Int
val y: Int
val z: Int
if (isOdd) {
x = 1
y = 3
z = 5
} else {
x = 2
y = 4
z = 6
}
return x + y + z
}
fun b(isOdd: Boolean): Int {
val x = if (isOdd) 1 else 2
val y = if (isOdd) 3 else 4
val z = if (isOdd) 5 else 6
return x + y + z
}
fun c(isOdd: Boolean): Int {
val (x,y,z) = if (isOdd) Triple(1, 3, 5) else Triple(2, 4, 6)
return x + y + z
}
输出
Test 0 - time 3
Test 1 - time 1
Test 2 - time 8
似乎我的第二个解决方案是最快的,接下来是我的第一个建议,而最佳答案要慢得多。
有人知道为什么会这样吗?显然这些是毫秒,所以它几乎总是无关紧要,但认为一种方法快 5-10 倍是很好的
编辑:
因此尝试将迭代次数增加到 100000000,结果是:
Test 0 - time 6
Test 1 - time 41
Test 2 - time 941
我猜前两个选项正在优化,但第三个选项总是创建一个新对象,使其速度很慢