Estoy tratando de sobrescribir un valor en una clase. Tengo el siguiente código:

open class Balloon() {
    open var textSize: Float = 20f
    init {
        Log.i("textSize", textSize.toString())
    }
}
    
class BigBalloon(): Balloon() {
    override var textSize = 30f
}

Sin embargo, el registro imprime estos valores:

enter image description here

El primer registro es de Balloon(), el segundo es de BigBalloon(). ¿Cómo puede imprimir 0.0 cuando lo sobrescribo como 30? ¿Implementé todo esto incorrectamente?

3
Maharkus 27 ago. 2020 a las 16:05

2 respuestas

La mejor respuesta

Por lo general, no se recomienda acceder a métodos abstractos (en este caso getTextSize) en el constructor, ya que podría generar artefactos como el suyo.

La anulación de la propiedad BigBaloon en realidad hace dos cosas:

  1. crea un nuevo campo interno - BigBaloon.textSize
  2. anula textSize getter y setter para acceder a ese campo

Es un poco contrario a la intuición, pero NO modifica el valor del campo Baloon.textSize, se deja intacto e inaccesible ya que el getter / setter ya no lo usa.

Su problema es cuando el padre de BigBaloon Baloon se está inicializando, accede a BigBaloon.textSize que NO se inicializa en este punto, por lo que devuelve cero.

3
Pawel 27 ago. 2020 a las 13:23

El orden de inicialización de Kotlin no es como lo entiende, el bloque init de la clase Base (Globo) se llama antes de que se realice la anulación. Se explica mejor en este respuesta. Y aquí está el orden de inicialización dado en documentos de Kotlin.

Coloque la propiedad en el constructor principal como:

Balloon(var textSize: Float = 20f) {
    // ...
}

Y cuando quieras cambiarlo, simplemente delegalo al constructor:

class BigBalloon: Balloon(30f)
2
Animesh Sahu 27 ago. 2020 a las 13:23