记录些容易遗忘或易混淆的语法结构和关键字
关键字
vararg 函数的变长参数 $ 用于字符串模板中变量名或变量值 is 类型检测 in 区间判断 inner 修饰内部类,内部类可以用this@Class 来获取外部类对象,外部类通过对象调用内部类方法,不用inner 修饰的类但写在内部称为嵌套类,外部类通过静态调用获取嵌套类对象,嵌套类不可通过this获取外部类对象 internal 同模块内可见 sealed 修饰密封类,类似于枚举,结合when条件语句使用,可列举出类的所以情况而不写else,这点比普通的switch要强,便于拓展时不遗漏新的属性 object 对象声明,可方便地实现对象单例 companion object 伴生对象,静态调用 by 委托,可实现类委托,属性委托,可委托给lazy{} 、Delegates.observable 、map
内联函数
函数 | 特点 | 使用 |
---|
let | it代指,强调作用域,返回最后一行或空,判null方便 | obj?.let{it.todo} | with | this代指可缺省,返回值为最后一行或return | with(user){todo} | run | this代指可缺省,返回值同with,判空方便 | obj?.run{todo} | apply | this代指可缺省,返回对象本身,适用初始化 | obj?.apply{todo} | also | it代指,返回对象本身,适用链式调用 | obj?.also{todo} |
协程
一个进程有多个线程,一个线程有多个协程,又称之为微线程,kotlin中默认实现了很多协程作用域,即各种各样的scope,可以用写同步代码的方式来书写异步代码
suspend 挂起函数,在协程内部使用,耗时任务会将协程挂起,直到任务完成,与阻塞不同点1.阻塞的进程依旧在内存中,挂起的进程被交换到内存外;2.阻塞一般是等待资源,挂起一般是用户或系统的需要3.阻塞在有资源后激活,挂起在用户主动激活
有个形象的比喻
挂起线程的意思就是你对主动对雇工说:“你睡觉去吧,用着你的时候我主动去叫你,然后接着干活”。 使线程睡眠的意思就是你主动对雇工说:“你睡觉去吧,某时某刻过来报到,然后接着干活”。 线程阻塞的意思就是,你突然发现,你的雇工不知道在什么时候没经过你允许,自己睡觉了,但是你不能怪雇工,因为本来你让雇工扫地,结果扫帚被偷了或被邻居家借去了,你又没让雇工继续干别的活,他就只好睡觉了。至于扫帚回来后,雇工会不会知道,会不会继续干活,你不用担心,雇工一旦发现扫帚回来了,他就会自己去干活的。
launch 创建一个协程,接受三个参数: 1.CoroutineContext上下文,代表运行在哪种线程中,有四种模式Dispatchers.Default, Dispatchers.IO:挂起时运行在默认线程池,挂起恢复后运行在IO线程 Dispatchers.Main:运行在主线程,但主线程后面的代码会先执行,挂起恢复后也在主线程 Dispatchers.Unconfined:挂起恢复后在默认线程池中 也可以自己指定在自定义的线程池中运行; 2.CoroutineStart启动模式,DEAFAULT,ATOMIC,UNDISPATCHED,LAZY(需手动启动) 3.block闭包方法,传入要执行的操作 async 创建个带返回值得协程,返回值是Deferred,继承自Job,新增await方法接受返回值,等待过程中会挂起协程,有结果后恢复协程 withContext 不创建新的协程,在指定协程上运行 runBlocking 独立使用,delay会阻塞线程,主要用于交接阻塞式与挂起的非阻塞式协同运行的场景 job 构建协程得到的对象,可执行start()–开始,join()–等待执行完毕,cancel()–取消,cancelAndJoin()–等待协程执行完毕再取消
理解协程的运行流程,由于多个协程是运行在一个线程中,正常谁写前面谁先运行,运行完后运行下一个,运行过程中如果被挂起,则让出线程运行下一个,挂起恢复后等正在运行的协程运行完运行该协程
|