在本文中,您将学习在Kotlin中创建数据类。您还将了解数据类必须满足的要求及其标准功能。
可能会出现这样的情况: 您需要创建一个仅用于保存数据的类。在这种情况下,您可以将类标记为 data 以创建数据类。比如说,
data class Person(val name: String, var age: Int)
对于此类,编译器会自动生成:
copy()函数,equals()和hashCode()对以及主要构造函数的toString()形式
componentN() 函数
在详细讨论这些函数之前,让我们讨论数据类必须满足的要求。
要求如下:
主构造函数必须至少具有一个参数。
主构造函数的参数必须标记为val(只读)或 var(读写)。
类不能是开放的、抽象的、内部的或密封的。
该类可以扩展其他类或实现接口。 如果您使用的是1.1之前的Kotlin版本,则该类只能实现接口。
data class User(val name: String, val age: Int)
fun main(args: Array<String>) {
    val jack = User("jack", 29)
    println("name = ${jack.name}")
    println("age = ${jack.age}")
}运行该程序时,输出为:
name = jack age = 29
当您声明一个数据类时,编译器会在后台自动生成几个函数,如toString()、equals()、hashcode()等。 这有助于保持代码的简洁性。 如果您使用Java,则需要编写大量样板代码。
让我们使用以下函数:
对于数据类,可以使用copy()函数创建具有不同属性的对象副本。 它的工作原理如下:
data class User(val name: String, val age: Int)
fun main(args: Array<String>) {
    val u1 = User("John", 29)
   
    //使用复制函数创建对象
    val u2 = u1.copy(name = "Randy")
    println("u1: name = ${u1.name}, name = ${u1.age}")
    println("u2: name = ${u2.name}, name = ${u2.age}")
}运行该程序时,输出为:
u1: name = John, name = 29 u2: name = Randy, name = 29
toString()函数返回该对象的字符串表示形式。
data class User(val name: String, val age: Int)
fun main(args: Array<String>) {
    val u1 = User("John", 29)
    println(u1.toString())
}运行该程序时,输出为:
User(name=John, age=29)
hasCode() 方法返回对象的散列码。 如果两个对象相等,则hashCode()会产生相同的整数结果。
如果两个对象相等(hashCode()相同),则equals()返回true。如果对象不相等,equals()返回false。
data class User(val name: String, val age: Int)
fun main(args: Array<String>) {
    val u1 = User("John", 29)
    val u2 = u1.copy()
    val u3 = u1.copy(name = "Amanda")
    println("u1 hashcode = ${u1.hashCode()}")
    println("u2 hashcode = ${u2.hashCode()}")
    println("u3 hashcode = ${u3.hashCode()}")
    if (u1.equals(u2) == true)
        println("u1 等于 u2.")
    else
        println("u1 不等于 u2.")
    if (u1.equals(u3) == true)
        println("u1 等于 u3.")
    else
        println("u1 不等于 u3.")
}运行该程序时,输出为:
u1 hashcode = 71750738 u2 hashcode = 71750738 u3 hashcode = 771732263 u1 等于 u2. u1 不等于 u3.
您可以使用解构声明将一个对象分解为多个变量。例如:
data class User(val name: String, val age: Int, val gender: String)
fun main(args: Array<String>) {
    val u1 = User("John", 29, "Male")
    val (name, age, gender) = u1
    println("name = $name")
    println("age = $age")
    println("gender = $gender")
}运行该程序时,输出为:
name = John age = 29 gender = Male
这是可能的,因为编译器会为数据类生成component()函数的所有属性。 例如:
data class User(val name: String, val age: Int, val gender: String)
fun main(args: Array<String>) {
    val u1 = User("John", 29, "Male")
    println(u1.component1())     // John
    println(u1.component2())     // 29  
    println(u1.component3())     // "Male"
}运行该程序时,输出为:
John 29 Male