null安全是Kotlin语言对Java的重大改进之一,可以避免Java的NullPointerException(简称NPE)。
一、非空类型和可空类型
只有可空类型的变量或常量才能接受null,非空类型的变量或常量不能接受null。
Kotlin对可空类型进行了限制:如果不加任何处理,可空类型不允许直接调用方法、访问属性。
var aStr:String="hello"
var bStr:String?="hello"
// aStr=null//错误
bStr=null
println(aStr.length)
// println(bStr.length)//编译不通过
二、先判断后使用
可空类型的变量不允许直接调用方法或属性,可以先判断该变量不为null,然后再调用该变量的方法或属性。
var b: String? = "hello"
var len = if (b != null) b.length else -1
println("b的长度:$len")
b = null
//先判断b不为null,然后调用b的length属性
if (b != null && b.length > 0) {
println(b.length)
} else {
println("空字符串")
}
Kotlin的if条件必须是Boolean类型,Boolean?与Boolean本质上是两种不同的类型。
三、安全调用
var b: String? = "hello"
println(b?.length)
b = null
println(b?.length)
输出结果:
5
null
上例中变量b的类型是String?,因此使用"?."安全调用来访问b的length属性,当b为null时,程序也不会放生NPE,而是返回null。
安全调用还可与let全局函数结合使用:
val myArr: Array<String?> = arrayOf("hello", "world", null, "intresting")
for (item in myArr) {
item?.let {
println(it)
}
}
输出结果:
hello
world
intresting
四、Elvis运算
Elvis运算其实就是if else的简化写法。
var b: String? = "hello"
var len = if (b != null) b.length else -1
println("b的长度:$len")
b = null
//使用Elvis运算符
var len2 = b?.length ?: -1
println("b的长度:$len2")
输出结果:
b的长度:5
b的长度:-1
由上例可见,"?:"其实就是if分支的简化写法。其含义是:如果"?:"左边的表达式不为null,则返回左边表达式的值,否则返回"?:"右边表达式的值。
五、强制调用
Kotlin也提供了强制调用,使用“!!.”
即可强制调用可空变量的方法或属性,不过可能会引发NPE。
var b: String? = "hello"
println("b的长度:${b!!.length}")
b = null
//下面代码引发空指针异常(NPE)
println("b的长度:${b!!.length}")
当可空变量b为null时,b!!.length将会引发NPE。
强制调用也可以作用于let()函数,此时不管item元素是否为null,程序都会对该元素调用let()函数,因此也是可能导致NPE。
学海无涯苦作舟
![](https://img.haomeiwen.com/i4625756/1e4bf2f119027169.jpg)
网友评论