Kotlin learning: Kotlin data classes and sealed classes

Kotlin data class and sealed class

Data type

Kotlin can create a class that only contains data, the keyword is data

data class User(val name: String, val age: Int)

The compiler will automatically extract the following functions from the main constructor based on all declared attributes:

  • equals() / hashCode()
  • toString() Format like "User(name=John, age=42)"
  • componentN() functions Correspond to attributes, arranged in order of declaration
  • copy() function

If these functions have been clearly defined in the class or inherited from the super class, they will no longer be generated

In order to ensure the consistency and meaning of the generated code, the data class needs to meet the following conditions:

  • The main constructor contains at least one parameter.

  • All the parameters of the main constructor must be marked as val or  var ;

  • Data class is not declared  abstractopensealed or  inner;

  • Data classes cannot inherit other classes (but can implement interfaces).

copy

To copy, use the copy() function, we can use this function to copy objects and modify some properties. For the User class above, the implementation will be similar to the following

fun copy(name: String = this.name, age: Int = this.age) = User(name, age)

Instance

Use the copy class to copy the User data class and modify the age attribute

data class User(val name: String, val age: Int)


fun main(args: Array<String>) {
    val jack = User(name = "Jack", age = 1)
    val olderJack = jack.copy(age = 2)
    println(jack)
    println(olderJack)

}

The output result is

User(name=Jack, age=1)
User(name=Jack, age=2)

Data class and deconstruction declaration

Component functions allow data classes to be used in destructuring declarations

val jane = User("Jane", 35)
val (name, age) = jane
println("$name, $age years of age") // prints "Jane, 35 years of age"

Standard data class

The standard library provides Pair and Triple. In most cases, naming the data class is a better design choice because the code is more readable and provides meaningful names and attributes

Sealed

Sealed classes are used to express restricted class inheritance structure: when a value is a limited number of types, but there can be no other types. In a sense, they are an extension of the enumeration class: the value set of the enumeration type is also limited, but there is only one instance of each enumeration constant, and a subclass of the sealed class can have more states that can contain Examples.

Declare a sealed class and use sealed to modify the class. The sealed class can have subclasses, but all subclasses must be embedded in the sealed class.

sealed cannot modify interface, abstract class (warning will be reported, but compilation errors will not occur)

sealed class Expr
data class Const(val number: Double) : Expr()
data class Sum(val e1: Expr, val e2: Expr) : Expr()
object NotANumber : Expr()

fun eval(expr: Expr): Double = when (expr) {
    is Const -> expr.number
    is Sum -> eval(expr.e1) + eval(expr.e2)
    NotANumber -> Double.NaN
}

The key advantage of using sealed classes is that when using when expressions, if you can verify that the statement covers all situations, you don't need to add an else clause to the statement.

fun eval(expr: Expr): Double = when(expr) {
    is Expr.Const -> expr.number
    is Expr.Sum -> eval(expr.e1) + eval(expr.e2)
    Expr.NotANumber -> Double.NaN
    // 不再需要 `else` 子句,因为我们已经覆盖了所有的情况
}

 

Guess you like

Origin blog.csdn.net/PrisonJoker/article/details/113777384