Métodos Mágicos En La Programación Orientada A Objetos

Métodos mágicos en la programación orientada a objetos

Como cantó Alfredo Mercurio en su album Kind Of Magic, hoy vamos a hablar de magia y la magia en la programación orientada a objetos la podemos encontrar gracias a los métodos mágicos, valga la redundancia, así que vamos a ver un listado de diferentes métodos mágicos que podemos utilizar en nuestras aplicaciones para hacerlas mas ricas. Ale a darle…

¿Qué son los métodos mágicos?

Lo primero que tenemos que tener claro sobre los métodos mágicos es que son métodos que se invocan en nuestra aplicación cuando suceden ciertos eventos y que podemos aprovechar para realizar acciones en nuestros objetos.

Es como cuando automáticamente Miquel Iceta se pone a bailar sin poder remediarlo cada vez que escucha La Gozadera sintiendo el ritmo in the body.

Pues lo mismo pasa con los métodos mágicos, existe un desencadenador y una acción a realizar.

En PHP tenemos un conjunto de 15 métodos mágicos que se agrupan por su finalidad y cuyos nombres son reservados por el motor del lenguaje lo que quiere decir que no podremos crear nosotros otros métodos que se llamen igual.

Un método mágico es fácil de reconocer porque su nombre viene precedido de dos barras bajas y según las buenas prácticas en la programación se recomienda no utilizar este tipo de nombrar métodos a no ser que tengamos que utilizar algunos de estos métodos mágicos.

Métodos __sleep() y __wakeup()

Tipicamente utilizamos el método mágico __sleep() para confirmar datos pendientes o para hacer funcionalidades similares a la limpieza de datos. Como a lo mejor esto no se entiende mucho tenemos que saber que cuando vamos a serializar un objeto, el método serialize() va a buscar si existe este método mágico en nuestra clase para ejecutarlo antes de la serialización por lo que podríamos utilizarlo como si se tratase un de evento de tipo PRE_EVENT.

Si escribes este método mágico en tu clase pero haces que no devuelva nada, cuando sea ejecutado va a devolver un NULL y si intentas serializar un NULL ahí si que vas a tener un pete de tres pares de cojones de tipo E_NOTICE.

Al igual que cuando se serializa un objeto se invoca al método __sleep(), pues cuando se deserializa un objeto mediante unserialize() también se ejecuta otro método mágico y en este caso se trata del __wakeup().

El uso típico que se da al método __wakeup() es restablecer la conexión con la base de datos que se haya podido perder durante el proceso de serialización/deserialización.

Método mágico __toString()

Este método me gusta especialmente y permite a las clases definir como se tienen que comportar cuando se les trata como si fuera un objeto de tipo string. Por ejemplo, si hacemos un echo de un objeto es este método el encargo de imprimir los valores de sus propiedades.

Obviamente no es obligatorio imprimir los valores de sus propiedades, puedes hacer que devuelva un saludo por ejemplo pero lo típico es eso y siempre ha de devolver un string, sino petará con el error fatal E_RECOVERABLE_ERROR.

Método __invoke()

Este método se ejecuta cuando se utiliza un objeto como si fuera una función. Puede parecer un poquito lioso pero con el siguiente ejemplo lo vas a ver muy claramente.

Método __set_state()

De entre todos los métodos mágicos este es ejecutado en aquellas clases que han sido exportadas mediante var_export(). ¿Y qué coño hace var_export() te preguntarás?

Pues es una función que obtiene información estructurada sobre la variable que le pasemos como argumento, el resultado que obtenemos con var_export() es parecido a var_dump() salvo que el código que se obtiene es código PHP válido.

Así pues, cuando en nuestro código hagamos una llamada a var_export() podremos controlar la salida de este si definimos su comportamiento en el método mágico __set_state().

Internamente al llamar a var_export() y a diferencia de otros métodos mágicos, no se comprueba si existe __set_state() en nuestra clase por lo que es nuestra responsabilidad comprobar que solamente se reimporten los objetos cuyas clases declaren este método mágico.

Método mágico __debugInfo()

Si el método __set_state() se ejecuta cuando se llama a var_export(). El método __debugInfo() se ejecutará cada vez que hagamos una llamada a var_dump() así de simple. Por defecto al llamar a var_dump() y no definir el método mágico en nuestra clase se mostrarán todas las propiedades de nuestra clase, las públicas, las protegidas y las privadas.

Este método mágico es una buena oportunidad para controlar qué propiedades de la clase han de mostrarse.

Método __clone()

En artículos anteriores ya hemos hablado del proceso de clonación de objetos. Pues este es el método mágico que se invoca cuando se clona un objeto. Pero a diferencia de otros métodos mágicos que actúan como un evento de tipo PRE_EVENT este método se ejecutará después de que la clonación se haya realizado para permitirnos hacer cambios sobre las propiedades del objeto, como si de un evento POST_EVENT se tratase.

Métodos mágicos __isset() y __unset()

Cuando queremos evaluar si un nodo existe en un array o cuando queremos saber si una variable tiene contenido o esta vacía, lo solemos hacer con las funciones isset() y empty() respectivamente. Pues bien el método mágico __isset() es invocado automáticamente (si existe) cuando hacemos uso de estas dos funciones.

Por otro lado, si en nuestra clase hemos definido el método mágico __unset(), este se ejecutará cuando hagamos uso de la función unset() sobre un miembro de nuestra clase.

Utilizamos la función unset() para destruir una variable dada. Esta función se comportará de una manera o de otra en función del ámbito y del tipo de variable. Para saber cómo se comportará puedes echar un vistazo a este link en el que se cuenta con detalle el funcionamiento de la función.

Métodos __set() y __get()

Utilizamos estos métodos mágicos cuando queremos redefinir el comportamiento al establecer y acceder a valores de propiedades inaccesibles y lo hacemos sobrecargando los métodos.

Para que se entienda, si quieres que cada vez que se establezca un valor para una propiedad de una clase se imprima un mensaje por pantalla, tendríamos que sobreesccribir el método __set() y escribir allí el nuevo comportamiento.

Con el método mágico __get() pasa lo mismo pero para cuando accedes al valor de una propiedad.

Métodos útiles que podemos utilizar para crear los getter y setters de una clase de una forma dinámica sin tener que escribir cada conjunto para cada propiedad de una clase, por ejemplo…

Métodos mágicos __call() y __callStatic()

El método __call() es invocado cuando intentamos acceder a métodos inaccesibles en el contexto de un objeto mientras que el método __callStatic() se invoca cuando accedemos a un método inaccesible en un contexto estático.

Como a lo mejor esto es un poquito güatdefak de entender, estoy seguro que con el siguiente ejemplo lo ves perfectamente.

Métodos __construct() y __destruct()

De estos métodos ya hablamos en artículos previos al curso y son invocados cuando instanciamos un objeto a partir de una clase o cuando destruimos un objeto respectivamente.

Tal vez el método destructor no lo utilices mucho, pero si tienes cierta experiencia en la programación orientada a objeto tendrás ya los huevos pelados de utilizar el constructor para inicializar variables de tu clase.

Es importante saber que si tienes una clase padre con un constructor que acepta dos argumentos mientras que la clase hija tiene un constructor con cinco no te va a fallar, así que tranquilo. Además para ejecutar el constructor de la clase padre desde el de la clase hija tendrás que hacerlo de la siguiente forma:

parent::__construct()

Por otro lado, el método destructor de una clase se ejecutará siempre cuando el motor de PHP ya no encuentre referencia alguna al objeto, así pues tipicamente los podemos utilizar para cerar conexiones a bases de datos o liberar memoria por ejemplo.

El método mágico destructor será invocado siempre sin ninguna excepción incluso cuando se detenga la ejecución del script mediante la función exit() pero si se llama a esta función dentro de un destructor se provocará que dejen de ejecutarse el resto de rutinas restantes a la finalización. Recuérdalo.

Pues nada, con esto ya hemos tocado el tema de los métodos mágicos. Si tienes dudas déjamelas a través de los comentarios o mediante twitter siguiendo el siguiente banner 😉

@gorkakatua #faqsGorkamu pregúntame por twitter cualquier cosa y vemos cómo lo solucionamos.

Hala a mamarla!

¿Te ha parecido este un artículo de 5 estrellas? Dame tu valoración:
Review Date
Reviewed Item
Métodos mágicos en la programación orientada a objetos
Author Rating
51star1star1star1star1star

Gorka Muñoz Andrés

Me llamo Gorka Muñoz y soy un desarrollador melómano. Combino a la perfección la búsqueda de nuevos grupos con la pasión por la tecnología. Desde chiquitito me ha gustado la programación, ahora que soy mayor estoy metido en el mundo del SEO sin olvidarme del /Dev.

Deja un comentario

Tu dirección de correo electrónico no será publicada. Los campos obligatorios están marcados con *