空指针检查
Android系统中,最常见的崩溃问题就是空指针异常,相信其他的系统或者程序,也会常常备受空指针问题的影响。这类问题只能由程序员自己主动通过逻辑判断来避免。可是,很难做到完全考虑到所有潜在的空指针异常。
Kotlin的做法则是将空指针异常检查提前到了编译期,在程序员写程序的时候,时刻能够检测出潜在的空指针问题,及时进行处理。
举例:
java代码
1 | public void doStudy(Study study){ |
这段代码java编译肯定没问题,但是他安全么?不一定。如果这个方法当中传入是一个null,将会导致空指针异常。
修改一下:
1 | public void doStudy(Study study){ |
这样才会安全。
转到kotlin:
1 | fun doStudy(study:Study){ |
对于kotlin来说,这是没有问题的,没有空指针的风险。因为,在kotlin当中,默认所有参数和变量都不能为空,所以这里传进来的study一定不为空。可以放心的调用它,一旦传入null,在编译的时候直接报错。
可空类型系统
1 | fun doStudy(study:Study?){ |
对于业务逻辑需要参数为null的话,kotlin提供的方法是,在参数类名后面加?号,但是函数里参数也是会被检测的,必须要有空的判断。
?.操作符
?.操作符:当对象不为空时正常调用,当为空时什么都不做。
1 | //上面的代码可以由?.操作符简化为 |
?:操作符
?:操作符:左右两边都接收一个表达式,如果左边结果不为空就返回左边结果,否则返回右边表达式结果
1 | val a = null |
相当于:
1 | val c = a ?: b |
!!.操作符
!!.操作符:非空断言工具,告知kotlin这里的对象不会为空,不用它做非空检查。出错可以抛异常。
1 | fun doStudy(study:Study?){ |
这个就和java的那个版本一样了,不安全了,照样运行报错了。
let函数
obj对象调用let函数,obj本身会作为参数传递到Lambda表达式中,当列表只有一个参数时用it。
用法:
1 | obj.let{ obj2 -> |
例子:
1 | fun doStudy(study:Study?){ |
let通常是和?.操作符结合,之前的study?.doHomework(),study?.readBooks()两个,相当于每次调用方法都需要对study做了if判空处理,相当麻烦。可以先study?. 如果study不为空就运行let,如果为空就什么都不做。此时let里面的lambda表达式当中的it肯定就不是空的了,因此let当中运行是安全的。
let的另一个优势:
let函数时可以处理全局变量的判空问题,而if语句是无法做到的
1 | var studyy : Study? = null; |
1 | //而let则没问题 |
Kotlin的小技巧
字符串内嵌表达式
Kotlin一开始就支持了字符串内嵌表达式,我们不再需要像java那样傻傻的拼接字符串了。
1 | "hello, ${obj.name}. nice to meet you" |
当表达式中仅有一个变量的时候,大括号可以省略
1 | "hello, $name. nice to meet you" |
kotlin的这种方式,不论是易读性易写性方面都比java更胜一筹
函数的参数默认值
简单来说就是,kotlin允许我们在定义函数的时候给任意参数设定一个默认值,这样当调用这个函数的时候不强求传此参数。
1 | fun printParams(num:Int, str:String = "hello") |
调用的时候可以
1 | printParams(123) |
当然默认值也可以给第一个参数
1 | fun printParams(num:Int = 0, str:String) |
那么填一个参数,就默认到num参数上了。问题不大,kotlin提供了键值对的方式来传参
1 | printParams(str = "Hello") |