请考虑以下示例:我有一个Animal的抽象类,每个动物都有一张嘴,但是由于每个动物的嘴都不同,所以该嘴类也很抽象:
abstract class Animal {
var numberLegs: Int = 4
var mouth: Mouth? = null
}
abstract class Mouth {
abstract fun makeSound()
}
我现在可以创建一个Dog和一个DogMouth:
class Dog: Animal() {
override var mouth: Mouth = DogMouth()
}
class DogMouth: Mouth() {
override fun makeSound() {
println("Bark!")
}
}
但是,这还允许我为狗指定其他类型的嘴,例如:
class CatMouth: Mouth() {
override fun makeSound() {
println("Meow!")
}
}
fun main() {
val dog = Dog()
dog.mouth.makeSound() // will print "Bark!"
dog.mouth = CatMouth() // I don't want this to work
dog.mouth.makeSound() // will print "Meow!"
}
设置override var mouth: DogMouth = DogMouth()
无效。
如何确保狗只具有DogMouths(以及其他狗的身体部位)?
答案 0 :(得分:0)
类似的问题已解决here和here。 解决方案是使用通用参数:
abstract class Animal<MouthType: Mouth> {
var numberLegs: Int = 4
abstract var mouth: MouthType
}
class Dog: Animal<DogMouth>() {
override var mouth: DogMouth = DogMouth()
}
这会使dog.mouth = CatMouth()
因类型不匹配而失败。
随着身体部位的增加,需要添加额外的泛型:
abstract class Animal<MouthType: Mouth, EarType: Ear, TailType: Tail> {
var numberLegs: Int = 4
abstract var mouth: MouthType
abstract var ear: EarType
abstract var tail: TailType
}