Kotlin基础知识_03-空指针检查
Kotlin基础知识_03-空值检查
1. 可空类型
Kotlin默认所有的参数和变量均都不可为空,如下面的code在编译时会报错:
提示 test()
方法不能输入空类型。
若要允许输入的类型为空,可以在类名的后面加上一个问号。比如,Int
表示不可为空的整型,而Int?
就表示可为空的整型;String
表示不可为空的字符串,而String?
就表示可为空的字符串类型。
如果要允许test()
方法中输入的类型为空,可以将 fun test(dog: Dog)
修改为 fun test(dog: Dog?)
:
fun test(dog: Dog?) {
dog.eat()
dog.run()
}
不过这样编译器仍然会提示错误:
原因很简单,因为当允许 dog 对象为空后,无论是调用 dog.eat()
还是调用 dog.run()
都有空指针异常的风险,因此才报错。解决办法只要给输入的对象做一个空值判断就可以了:
fun test(dog: Dog?) {
if (dog != null) {
dog.eat()
dog.run()
}
}
这样就可以正常编译通过了。不过如果每处检查代码都使用if判断语句,则会让代码变得比较啰嗦,kotlin提供了其它简化的写法。
2. 判空辅助工具 ?. 与 ?: 与 !!
2.1 操作符 ?.
借助 kotlin 新提供的 ?.
操作符,可将
if (dog != null) {
dog.eat()
}
语句简化成:
dog?.eat()
即:如果dog对象不为空,则调用 eat()
方法,dog对象为空,则不调用。
2.2 操作符 ?:
这个操作符的左右两边都接收一个表达式,如果左边表达式的结果不为空就返回左边表达式的结果,否则就返回右边表达式的结果。
借助 kotlin 新提供的 ?:
操作符,可将
val c = if (a ! = null) {
a
} else {
b
}
简化成
val c = a ?: b
小技巧:结合 ?. 和 ?: 操作符来获取文本长度
传统写法:
fun getTextLength(text: String?): Int {
if (text != null) {
return text.length
}
return 0
}
简化写法:
fun getTextLength(text: String?) = text?.length ?: 0
这里我们将?.
和?:
操作符结合到了一起使用,首先由于text是可能为空的,因此我们在调用它的length字段时需要使用?.
操作符,而当text为空时,text?.length
会返回一个null值,
这个时候我们再借助?:
操作符让它返回0。
2.3 操作符 !!
kotlin的 if 判断语句有时候会处理不了全局变量的判空问题,如下面的code:
var content: String? = "hello"
fun main() {
if (content != null) {
printUpperCase()
}
}
fun printUpperCase() {
val upperCase = content.toUpperCase()
println(upperCase)
}
已在main()
函数中判断过全局变量 content
不会为空,但是编译器仍然会报错:
如果确保此处一定不会为null, 可以使用非空断言操作符 !!
, 只需要在变量名后面加上 !!
即可:
fun printUpperCase() {
val upperCase = content!!.toUpperCase()
println(upperCase)
}
PS: 此操作符慎用。
3. 其它辅助工具- let() 函数
利用let()
函数可以进一步简化if 语句的判断:
let()
函数会以调用的对象作为参数,并调用指定的代码块并返回最终结果。
如:
fun test(dog: Dog?) {
dog?.eat()
dog?.run()
}
可简化成:
fun test(dog: Dog?) {
dog?.let {
it.eat()
it.run()
}
}
这样就不用针对所有调用dog对象的地方都做一次非空处理了。