Kotlin 是一门功能强大且灵活的编程语言,除了基础语法外,它还提供了许多高级特性,可以帮助你编写更简洁、高效和可维护的代码。以下是 Kotlin 的一些高级用法,涵盖了协程、扩展函数、属性委托、内联类、反射等内容。
- 协程(Coroutines)
协程是 Kotlin 中用于简化异步编程的核心特性。它允许你以同步的方式编写异步代码,避免回调地狱。
1.1 基本用法
import kotlinx.coroutines.*
fun main() = runBlocking {
launch {
delay(1000) // 非阻塞延迟
println("World!")
}
println("Hello,")
}
runBlocking:阻塞当前线程,直到协程执行完毕。
launch:启动一个新的协程。
1.2 异步返回值
使用 async 和 await 获取异步结果:
fun main() = runBlocking {
val result = async {
delay(1000)
"Hello, World!"
}
println(result.await()) // 输出:Hello, World!
}
1.3 结构化并发
通过 CoroutineScope 管理协程的生命周期:
fun main() = runBlocking {
val scope = CoroutineScope(Dispatchers.Default)
scope.launch {
delay(1000)
println("Task completed")
}
delay(500) // 等待一段时间
scope.cancel() // 取消协程
}
- 扩展函数(Extension Functions)
扩展函数允许你为现有类添加新方法,而无需修改其源代码。
2.1 基本用法
fun String.isPalindrome(): Boolean {
return this == this.reversed()
}
fun main() {
println("racecar".isPalindrome()) // 输出:true
}
2.2 扩展属性
val String.lastChar: Char
get() = this[length - 1]
fun main() {
println("Kotlin".lastChar) // 输出:n
}
- 属性委托(Property Delegation)
属性委托允许你将属性的 getter 和 setter 逻辑委托给另一个对象。
3.1 使用 lazy 实现懒加载
val lazyValue: String by lazy {
println("计算值")
"Hello"
}
fun main() {
println(lazyValue) // 第一次访问时计算
println(lazyValue) // 直接使用缓存值
}
3.2 使用 Delegates.observable 监听属性变化
import kotlin.properties.Delegates
var observedValue: String by Delegates.observable("初始值") { _, old, new ->
println("值从 $old 变为 $new")
}
fun main() {
observedValue = "新值" // 输出:值从 初始值 变为 新值
}
- 内联类(Inline Classes)
内联类用于封装一个值,同时避免运行时开销。
4.1 基本用法
inline class Password(val value: String)
fun main() {
val password = Password("123456")
println(password.value) // 输出:123456
}
4.2 优化性能
内联类在运行时会被替换为原始值,避免额外的对象分配。
- 反射(Reflection)
反射允许你在运行时检查类和对象的属性和方法。
5.1 获取类的信息
import kotlin.reflect.full.memberProperties
data class User(val name: String, val age: Int)
fun main() {
val user = User("Alice", 25)
val properties = User::class.memberProperties
for (property in properties) {
println("${property.name} = ${property.get(user)}")
}
}
5.2 动态调用方法
import kotlin.reflect.full.functions
class Calculator {
fun add(a: Int, b: Int): Int = a + b
}
fun main() {
val calculator = Calculator()
val addFunction = Calculator::class.functions.find { it.name == "add" }!!
val result = addFunction.call(calculator, 2, 3) as Int
println(result) // 输出:5
}
- 高阶函数与 Lambda 表达式
高阶函数是指以函数作为参数或返回值的函数。
6.1 基本用法
fun operateOnNumbers(a: Int, b: Int, operation: (Int, Int) -> Int): Int {
return operation(a, b)
}
fun main() {
val sum = operateOnNumbers(2, 3) { x, y -> x + y }
println(sum) // 输出:5
}
6.2 内联函数
使用 inline 关键字避免 Lambda 表达式的运行时开销:
inline fun measureTime(block: () -> Unit) {
val start = System.currentTimeMillis()
block()
val end = System.currentTimeMillis()
println("耗时:${end - start} 毫秒")
}
fun main() {
measureTime {
Thread.sleep(1000)
}
}
- 密封类(Sealed Classes)
密封类用于表示受限的类层次结构,子类必须在同一文件中定义。
7.1 基本用法
sealed class Result
data class Success(val data: String) : Result()
data class Error(val message: String) : Result()
fun handleResult(result: Result) {
when (result) {
is Success -> println("成功:${result.data}")
is Error -> println("错误:${result.message}")
}
}
fun main() {
val result = Success("数据加载成功")
handleResult(result) // 输出:成功:数据加载成功
}
- 泛型与型变
8.1 泛型类
class Box<T>(val value: T)
fun main() {
val box = Box(42)
println(box.value) // 输出:42
}
8.2 型变(Variance)
协变(out):允许子类型替换父类型。
class Producer<out T>(val value: T)
逆变(in):允许父类型替换子类型。
class Consumer<in T> {
fun consume(value: T) {
println(value)
}
}
- DSL(领域特定语言)
Kotlin 的 DSL 功能允许你创建领域特定语言,使代码更具表现力。
9.1 构建 HTML DSL
class HTML {
fun body(block: Body.() -> Unit) {
val body = Body()
body.block()
println(body)
}
}
class Body {
var content: String = ""
fun p(block: () -> String) {
content += "<p>${block()}</p>"
}
}
fun html(block: HTML.() -> Unit): HTML {
val html = HTML()
html.block()
return html
}
fun main() {
html {
body {
p { "Hello, World!" }
}
}
}
- 总结
Kotlin 的高级特性包括:
协程:简化异步编程。
扩展函数和属性:增强现有类的功能。
属性委托:简化属性逻辑。
内联类:优化性能。
反射:动态操作类和对象。
高阶函数与 Lambda:支持函数式编程。
密封类:受限的类层次结构。
泛型与型变:增强类型安全性。
DSL:创建领域特定语言。
掌握这些高级用法,可以让你在 Kotlin 中编写更高效、灵活和可维护的代码!