Manejo de métodos en Java

LIBP-0019 (Libro de pautas)

Aplicar buenas prácticas a la creación de métodos en Java permite optimizar el rendimiento y mejorar el mantenimiento de las aplicaciones construidas.

Pautas

TítuloCarácter
No fabricar métodos innecesariosObligatoria
Escribir métodos que solo hagan una cosa Obligatoria
Evitar el mal uso de los métodos get/setObligatoria
Hacer sólo lo necesario en los métodos constructoresObligatoria
Definir un constructor por defectoObligatoria
Asegurar la existencia de un método finalize para las clases que crean recursosObligatoria
Cómo definir un método finalizeObligatoria
Escribir un método main para cada clase relevanteRecomendada
Usar métodos finales cuando se quiera proteger de sobreescrituraObligatoria

No fabricar métodos innecesarios

Por el mismo principio que anteriormente las clases, debemos esperar a tener una auténtica necesidad para crear un método. Si no, corremos el riesgo de crear métodos que no se usen y puedan resultar difíciles de eliminar.

Escribir métodos que solo hagan una cosa

En particular, separar métodos que cambian estados de aquellos que los consultan. A veces es mejor manejar dos métodos Object finalPila() y Void eliminaCima() , que tenerlos todo en uno, Object Pop (). Con ello simplificamos el control de concurrencia y extensiones por herencia.

Evitar el mal uso de los métodos get/set

Con frecuencia elaboramos muchos métodos de acceso y consulta de datos. En muchas ocasiones no utilizamos la mayoría. Además, muchos atributos tienen dependencias entre ellos para mostrar un valor conjunto. La gestión individual de los mismos puede provocar errores.

Hacer sólo lo necesario en los métodos constructores

Intentar hacer los métodos de la forma más simple. Si incluimos llamadas a métodos que no sean finales, éstos podrían ser redefinidos causando errores en la construcción.

Se recomienda evitar las llamadas a métodos reemplazables (overridable) desde un constructor. Se corre el riesgo durante la construcción si se invocan métodos en un objeto construido de forma incompleta y puede ser difícil de discernir. Se puede salir de la subclase incapaz de construir su superclase o forzando a replicar el proceso de construcción completamente dentro de sí mismo, perdiendo la posibilidad de llamar a super(). Si el constructor por defecto contiene una llamada a un método reemplazable, la subclase puede no ser creada.

Definir un constructor por defecto

En el caso que existan constructores con argumentos, añadir un constructor que permita la construcción sin parámetros. Con esto facilitamos la carga dinámica de clases de tipo desconocido en tiempo de compilación mejorando el rendimiento de nuestras aplicaciones. Este constructor siempre tiene que ser comentado.

Asegurar la existencia de un método finalize para las clases que crean recursos

Es necesario para las clases que crean objetos, actualizan referencias, etc . Este método debe de eliminar los recursos creados por el constructor, normalmente en el orden inverso al que fueron creados.

Cómo definir un método finalize

Un método finalize debe implementarse siguiendo las siguientes recomendaciones:

  • Si se va a sobreescribir el método, es recomendable declararlo como protected. Si fuera público, otras clases pueden invocarlo.
  • Asegurar que se realizan acciones previas a la invocacion al método super.finalize(), aunque siempre debe llamar a este método.
  • Evitar que el método pueda ser llamado por el recolector de basura en un objeto, cuando la recolección de basura determina que no hay más referencias al objeto.
  • No debe de contener parámetros ya que implican confusión y provocan que la VM no los invoque.
  • Debe tener acceso privado, no declararlo como público.

Escribir un método main para cada clase relevante

Con ello facilitaremos los test y pruebas de la clase sirviendo para la creación de ejemplos. Normalmente este tipo de métodos se incluyen en planes de pruebas.

Usar métodos finales cuando se quiera proteger de sobreescritura

Si la creación de clases finales parece algo dura para nuestras necesidades, y realmente lo que se quiere es proteger son algunos métodos de una clase para que no sean sobreescritos, se puede utilizar la palabra clave "final" en la declaración del método para indicar al compilador que este método no puede ser sobreescrito por las subclases.

class AlgoritmodeAjedrez {
    . . .
    final void siguienteMovimiento(Pieza piezaMovida,
            PosicionenTablero nuevaPosicion) {
    }
    . . .
}