其他
Kotlin Vocabulary | 类型别名 typealias
作者 / David Winer, Kotlin 产品经理
有时候一些可读性差、不够明确或者名字太长的类型声明会干扰代码的 "自我表达"。这种情况下,可以使用 Kotlin 特别针对这个问题提供的特性: Typealias (本文下称 "类型别名")。类型别名可以使您在不增加新类型的情况下,为现有类或函数类型提供替代名称。
类型别名的使用
使用类型别名为函数类型命名:
typealias TeardownLogic = () -> Unit
fun onCancel(teardown : TeardownLogic){ }
private typealias OnDoggoClick = (dog: Pet.GoodDoggo) -> Unit
val onClick: OnDoggoClick
typealias TeardownLogic = () -> Unit
typealias TeardownLogic = (exception: Exception) -> Unit
fun onCancel(teardown : TeardownLogic){
// 无法轻易知晓可以从 TeardownLogic 得到什么信息
}
typealias Doggos = List<Pet.GoodDoggo>
fun train(dogs: Doggos){ ... }
如果您正使用的某个类名称很长,您可以使用类型别名来缩短它:
typealias AVD = AnimatedVectorDrawable
import android.graphics.drawable.AnimatedVectorDrawable as AVD
导入别名 (import alias)
https://kotlinlang.org/docs/reference/packages.html#imports
import io.plaidapp.R as appR
import io.plaidapp.about.R
由于类型别名需要在类的外部声明,所以使用时您需要考虑约束它们的可见性。
在多平台工程中使用类型别名
在使用 Kotlin 开发多平台工程时,您可以在公共代码 (common code) 中写一个接口,并在相应的平台代码中实现这个接口。Kotlin 提供了 "实际声明" (actual declarations) 和 "预期声明" (expected declarations) 的机制来简化这种操作。在公共代码中声明的接口为预期声明,使用 expect 关键字;在相应的平台代码中的扩展为实际声明,使用 actual 关键字。如果平台代码中已经实现了公共代码中的某个接口,并且所有期望方法的签名一致时,您可以使用类型别名将实际声明的类型名称映射到期望类型上:
expect annotation class Test
actual typealias Test = org.junit.Test
多平台工程
https://kotlinlang.org/docs/reference/platform-specific-declarations.html
工作原理
// Kotlin
typealias Doggos = List<Pet.GoodDoggo>
fun train(dogs: Doggos) { ... }
fun play(dogs: Doggos) { ... }
// 反编译后 Java 代码
public static final void train(@NotNull List dogs) { … }
public static final void play(@NotNull List dogs) { … }
fun play(dogId: Long)
typealias DogId = Long
fun pet(dogId: DogId) { … }
fun usage() {
val cat = Cat(1L)
pet(cat.catId) // compiles
}
推荐阅读