在 Kotlin 开发 8 个月后,我才开始意识到这个 smart cast,而且我可能在不知情的情况下一直在使用它。Android Studio IDE 负责处理它!
假设你有BaseClass并且ChildClass喜欢这个。
open class BaseClass
class ChildClass(val value: Int): BaseClass()
并且,您创建ChildClass对象并被BaseClass
val obj: BaseClass = ChildClass(value = 7)
要访问 中的数据ChildClass,请在下面进行显式转换。
val childObj = obj as ChildClass
childObj.value
但是 Kotlin 编译器可以在以下情况下自动为您智能转换:
示例 1
fun smartCastExample1() {
val obj: BaseClass = ChildClass(value = 7)
//Calling obj.value here is not allowed
//because obj belongs to BaseClass
if (obj is ChildClass) {
//obj in this scope is smart cast to ChildClass.
//Thus, accessing the obj.value is allowed here
println("Child value is ${obj.value}")
//You don't need to explicit cast like this
val childObj = obj as ChildClass
println("Child value is ${childObj.value}")
}
}
obj在这个if范围内必须是ChildClass,因此 Kotlin 编译器智能转换它
示例 2
fun smartCastExample2() {
val obj: BaseClass = ChildClass(value = 7)
if (obj !is ChildClass) return
// obj is smart cast to ChildClass
println("Child value is ${obj.value}")
}
obj必须在这里,ChildClass因为如果不是,它已被退回。
示例 3
fun smartCastExample3() {
val obj: BaseClass = ChildClass(value = 7)
// obj at right side of || is smart cast to ChildClass
if (obj !is ChildClass || obj.value == 7) return
}
这只在 is 时被obj.value评估。如果您更改为,则智能演员表将不起作用。objChildClassobj !is ChildClassobj is ChildClass
示例 4
fun smartCastExample3() {
val obj: BaseClass = ChildClass(value = 7)
// obj at right side of && is smart cast to ChildClass
if (obj is ChildClass && obj.value == 7) return
}
与上面的示例类似,第二次检查仅在 is 时进行obj评估ChildClass。如果您更改obj is ChildClass为obj !is ChildClass,则智能演员表将不起作用。
这里的例子是从超类型转换为子类型。它也适用于可空类型到不可空类型。