Patron de Diseño Singleton

PATRÓN DE DISEÑO SINGLETON Contexto

Existen escenarios donde la aplicación solo necesita emplear una única instancia (objeto) de una clase, y esta instancia debe ser accesible desde diferentes partes del sistema.
Las clases que cumplen estas características suelen tener alguna de estas funciones:
  • Controlar el acceso a un recurso que por su naturaleza no admite el acceso concurrente (impresora, socket, fichero).
  • Obtener referencias de clases que actúan como servidoras de recursos (pool de conexiones).
  • Ejecutar código carente de estado (si el estado no cambia solo necesitamos una instancia).
  • Mantener un estado que debe ser globalmente único.
Por ejemplo, un sistema de log se ajusta a estas car
acterísticas porque:
  • Controla el acceso al recipiente de la información de log.
  • Toda la información del log se envía a través de un punto único.
  • Su único estado es la configuración, que es global y no suele variar.
Problema
Necesitamos crear una instancia de un clase que sea accesible globalmente, y que sea única.
Solución
El patrón Singleton proporciona la siguiente solución:
  • Hacer que la clase provea una instancia de sí misma.
  • Permitir que otros objetos obtengan esa instancia, mediante la llamada a un método de la clase.
  • Declarar el constructor como privado, para evitar la creación de otros objetos.
El diagrama UML correspondiente es muy simple y se muestra en la siguiente figura.

Este diagrama UML muestra como se implementa el patrón Singleton en una clase. Contiene una propiedad estática (el subrayado indica que es un método de clase) de nombre instancia, y que el método getInstancia() retorna un objeto de la misma clase.
Según la notación UML el número 1 en la esquina superior derecha, indica que solamente habrá una instancia de esta clase. El signo "-" en el constructor, lo señala como privado. Esto consigue que nadie aparte de la propia clase, pueda crear una instancia.
Implementación en PHP
Una primera implementación (GoF) de este patrón considera la instanciación de la clase en el método getInstancia(), tal como se ilustra a continuación:
class Demo{ 

    private static $instancia = null;  

    public static function getInstancia(){  

        if( self::$instancia == null ){  
            self::$instancia = new Demo();  
        }  
        return self::$instancia;  

    }  

    private function __construct() {  
    } 

    . . .   . . .  

}
Una segunda implementación considera la instanciación de la clase en la misma instrucción donde se declara la variable $instancia, tal como ilustra a continuación:

class Demo{ 

    private static $instancia = new Demo();  

    public static function getInstancia(){  
        return self::$instancia;  
    }  

    private function __construct() {  
    } 

    . . .   . . .  

}
El acceso a la instancia se realiza de la siguiente manera:
$demo = Demo::getInstancia();
Implementación en Java
Una primera implementación (Gof) de este patrón considera la instanciación de la clase en el método getInstancia(), tal como se ilustra a continuación:
public class Demo{ 

    private static Demo instancia = null;  

    public static Demo getInstancia(){  

        if( instancia == null ){  
            instancia = new Demo();  
        }  
        return instancia;  

    }  

    private Demo() {  
    } 

    . . .   . . .  

}
Una segunda implementación considera la instanciación de la clase en la misma instrucción donde se declara la variable instancia, tal como ilustra a continuación:
public class Demo{

private static Demo instancia = new Demo(); 

public static Demo getInstancia(){ 
return instancia; 
} 

private Demo() { 
}

. . .   . . . 

}
El acceso a la instancia se realiza de la siguiente manera:

    Demo demo = Demo.getInstancia();
Comentarios

Si estamos en un ambiente de un solo hilo (single-thread) la primera implementación es suficiente. En contrapartida, tiene serios problemas en entornos multihilo (multi-thread) dado que, debido a cuestiones de sincronización y concurrencia, puede crearse más de una instancia. ¿Cómo puede ser esto posible? Imaginemos que dos hilos evalúan la condición $instancia == null ( en Java: instacia == null ) y en ambos casos es verdadera. En este caso, ambos hilos crearán la instancia, violando el propósito del patrón Singleton.
Para solucionar el problema de que existe la posibilidad de crear mas de una instancia en entornos multihilo puede utilizar la segunda implementación.

CÓDIGO FUENTE

En esta sección te presento un video de una aplicación web desarrollada SPRING FRAMEWORK y MYSQL.

Tú tienes acceso al código fuente de esta aplicación, después del video tienes el enlace.




No hay comentarios:

Publicar un comentario