【kotlin】构造器-主构造器与次构造器

sdkei 作于2019年04月11日:原文

解说主构造器与次构造器
官方文献参考Classes and Inheritance - Kotlin Programming Language

对象读者


知道类的基本定义方法的人

主构造器

基本的类定义如下

1
class MyClass(....) {...}

(...)就是构造器的定义
在类定义的代码块{...}外面定义的构造器称为主构造器(区别于后面的次构造器)。

不省略

上面的写法其实是省略的写法。
不省略的话是下面这样。

1
class MyClass constructor( ... ) { ... }

指定主构造器的可视性与注解的时候要使用不省略的写法

1
class MyClass @Deprecated("Use YourClass class.") private constructor() {}

更加省略

主构造器没有参数的时候()也能省略。

1
class MyClass {}

另外用写constructor的写法的时候,即便没有参数()也不能省略。

次构造器


因为kotlin可以给参数设定默认值,大多数场合一个构造器也就够了。
话是这么说,但定义多个构造器也是可以的。

主构造器之外的构造器称为次构造器。
次构造器在类定义的代码块{...}当中定义。

1
2
3
4
class MyClass {
constructor( ... ) { ... } // セカンダリーコンストラクターの1つ
constructor( ... ) { ... } // セカンダリーコンストラクターの1つ
}

constructor( ... ) 后面的{ ... }如果是空的话是能省略的。
次构造器就算没有参数()也是不能省略的

调用其它构造器

次构造器能调用其它构造器。
因此,constructor(...)之后能付有: this(...)

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
class MyClass(int: Int) {
// 调用主构造器所进行的处理。
init {
println(int)
}

constructor(short: Short) : this(short + 1)
// ↑调用参数为Int类型的某个构造器(主构造器)
constructor(byte: Byte) : this((byte + 1).toShort()) // 参数
// ↑调用参数为Short类型的某个构造器(另一个次构造器)。
}

fun main() {
MyClass(0) // > 0
MyClass(0.toShort()) // > 1
MyClass(0.toByte()) // > 2
}

次构造器必须直接或间接调用主构造器。

省略主构造器的()


关于主构造器的说明如下。

主构造器没有参数的时候,()可以省略。

这是在没有次构造器的时候才是对的。但在有次构造器的时候省略()的话主构造器就没了。
没有主构造器的时候,次构造器的: this()不要也无所谓。

1
2
3
4
5
6
7
8
9
class MyClass {
constructor(int: Int) : this() // 编译错误!
constructor(int: Int) // 没有调用其它次构造器的必要的话,不要写`: this( ... )`
constructor(short: Short) : this(short.toInt())
}

fun main() {
MyClass() // 编译错误!
}

构造器的参数var val


构造器的参数能添付var或者val,这样一来那个参数就能作为属性。

1
2
3
4
class MyClass(
val userId: String,
var age: Int
)

这与下面的写法等价

1
2
3
4
5
6
7
class MyClass(
userId: String,
age: Int
) {
val userId: String = userId
var age: Int = age
}

但是只有主构造器才能那个这样做。
想想也是理所当然的。
不论是哪个次构造器生成的实例,属性的有无发生了变化都是让人很头痛的事情。

总结


  • 写在类定义的代码块之外的是主构造方法,写在里面的是次构造方法。

  • 主构造器能省略constructor

    • 指定主构造器的可视性或者注解的时候不能省略
  • 没有明示主构造器的时候(constructor(...)都没有写)

    • 没有次构造器的话,作成没有参数的主构造器
    • 有次构造器的话,不作成主构造器
  • 次构造器使用: this(...)能调用主构造器或者其它次构造器

  • 有主构造器的时候,次构造器必须直接或者间接调用主构造器(需要写: this(...)

  • 构造器的参数添付var val可以使之成为属性

    • 只有在主构造器才能这样做
  • Copyright: Copyright is owned by the author. For commercial reprints, please contact the author for authorization. For non-commercial reprints, please indicate the source.
  • Copyrights © 2021-2022 Jokan
  • Visitors: | Views: