Evitar reemplazos con final
En la sesión de introducción a la programación orientada en objetos con PHP vimos que se podía usar la palabra reservada **final** para evitar que una clase fuera heredable. Si anteponemos también la palabra **final** delante de la definición de una función, ésta no podrá ser reemplazada por la subclase o clase hija.
Se usa en API de clases, por ejemplo, Exception
Ejemplo de clase que no puede ser heredable:
<?php
final class Alumno extends Persona {..}
class PAS extends Alumno
{
}
?>
Nos proporcionará este error fatal:
Fatal error: Class PAS may not inherit from final class (Persona) in ..
Ejemplo de método que no queremos que sea reemplazado:
<?php
class A {
protected $atributo = "Valor por defecto";
final function operacion() {
echo "[operation()]<br>";
echo 'Valor de $atributo es ' . $this->atributo . "<br>";
}
}
class B extends A {
protected $atributo = "Valor modificado";
function operacion () {
echo "[funcion reemplazada en la clase B]<br>";
echo 'Valor de $atributo es ' . $this->atributo "<br>";
}
}
?>
Nos mostrará el siguiente error:
Fatal error: Cannot override final method A::operacion() in ..
Otro buen ejemplo de clase que contiene funciones no reemplazables es la definición de la clase Exception que veremos en la sesión de excepciones. A continuación vemos un esbozo de lo que puede ser su definición:
class Exception {
protected $message = 'Unknown exception'; // exception message
protected $code = 0; // user defined exception code
protected $file; // source filename of exception
protected $line; // source line of exception
function __construct($message = null, $code = 0);
/* Overrideable */
function __toString(); // formated string for display
final function getMessage(); // message of exception
final function getCode(); // code of exception
final function getFile(); // source filename
final function getLine(); // source line
final function getTrace(); // an array of the backtrace()
final function getTraceAsString(); // formated string of trace
}
Como vemos es una clase heredable de la cual podremos heredar sus atributos y métodos, pero donde no nos permiten reemplazar los métodos getMessage(), getCode(), etc. para modificar su funcionalidad o comportamiento.