Logotipo de ConstructiCat
CodeBust.
Explorar la sección ▾

Reemplazar Subclase con Campos.

Problema

Tienes subclases que se diferencian únicamente en sus métodos (que devuelven constantes).

Solución

Reemplaza los métodos con campos en la clase padre y elimina las subclases.

##Ejemplo

Antes
abstract class Person {
  abstract boolean isMale();
  abstract char getCode();
}
class Male extends Person {
  boolean isMale() { return true; }
  char getCode() { return 'M'; }
}
class Female extends Person {
  boolean isMale() { return false; }
  char getCode() { return 'F'; }
}
Después
class Person {
  private final boolean male;
  private final char code;

  private Person(boolean male, char code) {
    this.male = male;
    this.code = code;
  }
  static Person createMale() { return new Person(true, 'M'); }
  static Person createFemale() { return new Person(false, 'F'); }
  boolean isMale() { return male; }
  char getCode() { return code; }
}

##Por qué refactorizar

A veces la refactorización es justo lo que se necesita para evitar el código de tipos.

En uno de esos casos, una jerarquía de subclases puede diferir únicamente en los valores devueltos por determinados métodos. Estos métodos ni siquiera son el resultado de un cálculo, sino que están estrictamente definidos en los propios métodos o en los campos que estos devuelven. Para simplificar la arquitectura de clases, esta jerarquía puede comprimirse en una sola clase que contenga uno o varios campos con los valores necesarios, según la situación.

Estos cambios pueden ser necesarios tras mover una gran cantidad de funcionalidad de una jerarquía de clases a otro lugar. La jerarquía actual ya no es tan valiosa y sus subclases ahora son solo peso muerto.

##Ventajas

  • Simplifica la arquitectura del sistema. Crear subclases es excesivo si todo lo que quieres es devolver valores distintos en métodos distintos.

##Cómo refactorizar

  1. Aplica Reemplazar Constructor con Método de Fábrica a las subclases.

  2. Reemplaza las llamadas a los constructores de las subclases con llamadas al método de fábrica de la superclase.

  3. En la superclase, declara campos para almacenar los valores de cada uno de los métodos de las subclases que devuelven valores constantes.

  4. Crea un constructor protegido en la superclase para inicializar los nuevos campos.

  5. Crea o modifica los constructores existentes de las subclases para que llamen al nuevo constructor de la clase padre y le pasen los valores correspondientes.

  6. Implementa cada método constante en la clase padre de modo que devuelva el valor del campo correspondiente. Luego elimina el método de la subclase.

  7. Si el constructor de la subclase tiene funcionalidad adicional, usa Método en Línea para incorporar el constructor al método de fábrica de la superclase.

  8. Elimina la subclase.