Kotlin 属性

1、声明

关键字 var 声明为可变的

关键字 val 声明为只读的

Kotlin 复制代码
class Address {
    val name: String = "Holmes, Sherlock"
    val street: String = "Baker"
    var city: String = "London"
    var state: String? = null
    var zip: String = "123456"
}
2、使用

使用一个属性,以其名称引用它即可

Kotlin 复制代码
fun copyAddress(address: Address): Address {
    val result = Address()      // Kotlin 中没有"new"关键字
    result.name = address.name  // 将调用访问器
    result.street = address.street
    // ......
    return result
}
3、Getter 与 Setter

声明一个属性的完整语法

Kotlin 复制代码
var <propertyName>[: <PropertyType>] [= <property_initializer>]
    [<getter>]
    [<setter>]

其初始器(initializer)、getter 和 setter 都是可选的;属性类型如果可以从初始器, 或其 getter 的返回值(如下文所示)中推断出来,也可以省略

Kotlin 复制代码
var initialized = 1 // 类型 Int、默认 getter 和 setter
// var allByDefault // 错误:需要显式初始化器,隐含默认 getter 和 setter
4、只读属性不允许 setter
Kotlin 复制代码
val simple: Int? // 类型 Int、默认 getter、必须在构造函数中初始化
val inferredType = 1 // 类型 Int 、默认 getter
5、自定义的 getter、setter

可以为属性定义自定义的访问器

如果定义了一个自定义的 getter会覆盖默认的getter,每次访问该属性时都会调用它

Kotlin 复制代码
class Rectangle(val width: Int, val height: Int) {
    val area: Int
        get() = this.width * this.height  // 自定义getter

    // 属性类型是可选的,因为它可以从getter的返回类型中推断出来
    // val area get() = this.width * this.height
}

如果定义了一个自定义的 setter会覆盖默认的setter,每次给属性赋值时都会调用它

Kotlin 复制代码
var stringRepresentation: String
    get() = this.toString()
    set(value) {
        setDataFromString(value) // 解析字符串并赋值给其他属性
    }

可以定义访问器而不定义其实现,改变一个访问器进行注解或者改变其可见性,而不改变默认的实现

Kotlin 复制代码
var setterVisibility: String = "abc"
    private set // 此 setter 是私有的并且有默认实现

var setterWithAnnotation: Any? = null
    @Inject set // 用 Inject 注解此 setter
6、幕后字段

字段仅作为属性的一部分在内存中保存其值时使用,不能直接声明,使用 field 标识符在访问器中引用, field 只能用在属性的访问器内;若属性至少一个访问器使用默认实现, 或者自定义访问器通过 field 引用幕后字段,将会为该属性生成一个幕后字段

Kotlin 复制代码
var counter = 0            // 这个初始器直接为幕后字段赋值
    set(value) {
        if (value >= 0)
            field = value  // 赋值给 counter
    }

// 只读属性无setter,覆盖了默认getter实现,并且没有通过field引用,所以不生产幕后字段
val isEmpty: Boolean
    get() = this.size == 0
7、延迟初始化

lateinit 修饰符标记属性,可不在构造函数中初始化;只能用于在类体中的属性(不是在主构造函数中声明的 var 属性, 并且仅当该属性没有自定义 getter 或 setter 时),也用于顶层属性与局部变量;该属性或变量必须为非空类型,并且不能是原生类型

Kotlin 复制代码
public class MyTest {
    lateinit var subject: TestSubject

    @SetUp fun setup() {
        subject = TestSubject()
    }

    @Test fun test() {
        subject.method()  // 直接解引用
    }
}

.isInitialized 检测一个 lateinit var 是否已经初始化过

Kotlin 复制代码
if (foo::bar.isInitialized) {
    println(foo.bar)
}
相关推荐
长亭外的少年12 小时前
Kotlin 编译失败问题及解决方案:从守护进程到 Gradle 配置
android·开发语言·kotlin
JIAY_WX12 小时前
kotlin
开发语言·kotlin
麦田里的守望者江20 小时前
KMP 中的 expect 和 actual 声明
android·ios·kotlin
菠菠萝宝1 天前
【YOLOv8】安卓端部署-1-项目介绍
android·java·c++·yolo·目标检测·目标跟踪·kotlin
恋猫de小郭1 天前
Kotlin Multiplatform 未来将采用基于 JetBrains Fleet 定制的独立 IDE
开发语言·ide·kotlin
枫__________2 天前
kotlin 协程 job的cancel与cancelAndJoin区别
android·开发语言·kotlin
鸠摩智首席音效师2 天前
如何在 Ubuntu 上配置 Kotlin 应用环境 ?
linux·ubuntu·kotlin
jikuaidi6yuan4 天前
Java与Kotlin在鸿蒙中的地位
java·kotlin·harmonyos
liulanba4 天前
Kotlin的data class
前端·微信·kotlin
小白学大数据4 天前
使用OkHttp进行HTTPS请求的Kotlin实现
爬虫·python·okhttp·https·kotlin