面试题答案
一键面试Kotlin 数据类特点
- 自动生成函数
- equals() 和 hashCode():数据类会自动根据主构造函数中声明的属性生成
equals()
和hashCode()
函数。这使得基于属性内容进行对象比较变得简单,例如:
- equals() 和 hashCode():数据类会自动根据主构造函数中声明的属性生成
data class User(val name: String, val age: Int)
val user1 = User("Alice", 25)
val user2 = User("Alice", 25)
println(user1 == user2) // 输出 true,因为根据自动生成的 equals 方法比较属性值
- toString():会自动生成一个包含所有属性的
toString()
方法,格式为类名(属性 1 = 值 1, 属性 2 = 值 2, ...)
。例如对于上述User
类,user1.toString()
可能输出User(name=Alice, age=25)
。 - copy():该方法允许复制一个对象并选择性地修改某些属性的值。例如:
val user3 = user1.copy(age = 26)
println(user3) // 输出 User(name=Alice, age=26)
- componentN() 函数:对于数据类,会为每个属性生成对应的
componentN()
函数,N 从 1 开始,对应属性声明的顺序。这使得数据类可以在解构声明中使用,如:
val (name, age) = user1
println("$name is $age years old") // 输出 Alice is 25 years old
- 使用场景
- 存储和传输数据:数据类非常适合用于存储和传输数据,例如在与服务器进行交互时,作为数据模型来封装从服务器获取的数据或向服务器发送的数据。例如,一个表示用户信息的 API 响应,可以用数据类来建模:
data class UserResponse(val id: Int, val name: String, val email: String)
- 不可变数据结构:由于数据类通常用于存储数据,并且通过
copy()
方法进行修改,很适合构建不可变的数据结构,保证数据的一致性和安全性。
与普通类在定义和使用上的差异
- 定义差异
- 数据类:在类声明前使用
data
关键字,并且主构造函数至少有一个参数。例如:
- 数据类:在类声明前使用
data class Point(val x: Int, val y: Int)
- 普通类:普通类定义不需要
data
关键字,构造函数参数也没有强制要求,例如:
class Shape {
var width: Int = 0
var height: Int = 0
constructor(width: Int, height: Int) {
this.width = width
this.height = height
}
}
- 使用差异
- 函数生成:数据类自动生成
equals()
、hashCode()
、toString()
、copy()
和componentN()
等函数,而普通类需要开发者手动实现这些函数,如果有需求的话。 - 对象比较:数据类基于属性值进行比较,普通类默认使用对象引用比较,除非手动重写
equals()
方法。 - 数据修改:数据类推荐使用
copy()
方法进行数据修改,保持对象的不可变性;普通类通常直接修改对象的属性值。例如对于数据类:
- 函数生成:数据类自动生成
val point1 = Point(1, 2)
val point2 = point1.copy(x = 3)
对于普通类:
val shape1 = Shape(10, 20)
shape1.width = 30