Os padrões de projetos nos ajudam estruturar nossos programas de maneiras mais flexíveis, fáceis de entender e manter. Através deles sistemas são construídos com boas qualidades de design orientado à objetos(OO). Eles nos fornecem soluções gerais para problemas de projeto. Esse artigo explica o padrão singleton mostrando seu uso e estrutura aplicada no contexto de uma classe de configuração pertencente à uma aplicação.
O padrão singleton garante que um e apenas um objeto seja instanciado para uma dada classe. De todos os padrões, o Singleton é o mais simples em termos de seu diagrama de classes.
Através do padrão singleton os objetos são criados apenas quando eles são necessários, ou seja, caso não seja preciso o objeto não será criado. A aplicação garante a utilização de um recurso global único que é acessado nas funcionalidades onde esse objeto é necessário para realização de uma determinada tarefa.
Você pode estar se perguntando o por quê de criar uma classe na qual só pode ser instanciado um único objeto. Em determinados contextos existem muitos objetos dos quais precisamos apenas de um: grupos de linhas, caixas de diálogo, objetos que cuidam de preferências e configurações de registro, objetos usados para registro e objetos que agem como drivers de dispositivos para dispositivos como impressoras e placas gráficas. Na verdade, para muitos desses objetos, se instanciássemos mais de uma vez, encontraríamos todos os tipos de problema, como comportamento inadequado de programa, uso excessivo de recursos ou resultados inconsistentes.
O diagrama de classes do padrão singleton é mostrado a seguir:
A variável de classe uniqueInstance contém nossa única instância de Singleton. O método getInstance() é estático, o que significa que é um método de classe, então você pode acessá-lo a partir de qualquer lugar de seu código usando Singleton.getInstance(). É tão fácil quanto acessar uma variável global, mas obtemos benefícios com a instanciação simples a partir de Singleton.
Como exemplo prático a classe ApplicationConfiguration implementa o padrão Singleton, conforme é mostrado a seguir:
package com.programacao4devs.singleton.configuration;
public class ApplicationConfiguration {
private static ApplicationConfiguration uniqueInstance;
// outras variáveis de instância úteis aqui
private ApplicationConfiguration() {}
public static ApplicationConfiguration getInstance() {
if ( uniqueInstance == null ) {
uniqueInstance = new ApplicationConfiguration();
}
return uniqueInstance;
}
// outros métodos úteis aqui
}
O problema no padrão Singleton utilizando contextos diferentes:
Uma aplicação pode ter contextos diferentes no qual é executado o seguinte trecho de código:
ApplicationConfiguration appConfiguration = ApplicationConfiguration.getInstance();
Nesse cenário, contextos diferentes pode conter diferentes objetos de ApplicationConfiguration, ou seja, mais de um objeto da classe ApplicationConfiguration é criado mesmo com a utilização do padrão singleton.
Para entender melhor esse caso é mostrado abaixo uma sequência de instruções que é executada pela JVM (Java Virtual Machine).
Solução ao problema do padrão singleton utilizando contextos diferentes
O problema do padrão singleton utilizando vários contextos pode ser resolvido com a alteração do método getInstance em um método sincronizado, conforme é mostrado abaixo:
public static synchronized ApplicationConfiguration getInstance() {
if ( uniqueInstance == null ) {
uniqueInstance = new ApplicationConfiguration();
}
return uniqueInstance;
}
Observação: sincronizar um método pode reduzir o desempenho em um fator de 100. Logo, se uma parte de tráfego alto de seu código começar usando getInstance(), talvez você tenha que reconsiderar.
Os princípios OO são:
Inscreva seu nome e email na Programacao4Devs para receber atualizações de novos artigos, tutoriais e dicas.
Sua inscrição foi registrada. Obrigado!