Una clase, una instancia y cero excusas: static y Singleton en Java

Un atributo static es un atributo que pertenece a la clase, no a los objetos creados a partir de ella.
Existe una única copia del atributo para toda la aplicación, compartida por todas las instancias.

  • Se declara con la palabra clave static.
  • Se accede usando el nombre de la clase.
  • No depende de ningún objeto concreto.
  • Se inicializa cuando la clase se carga en memoria.

Cuándo usarlo

  • Contadores globales.
  • Constantes compartidas.
  • Información común a todos los objetos.
  • Estados que deben ser únicos para la clase.

public class Jugador {
    private String nombre;
    private int puntos;
    public static int totalJugadores = 0;

    public Jugador(String nombre) {
        this.nombre = nombre;
        this.puntos = 0;
        totalJugadores++; // actualiza el contador compartido
    }
}


Si luego haces:

new Jugador("Ana");
new Jugador("Luis");
System.out.println(Jugador.totalJugadores); // Imprime 2
Da igual cuántos jugadores existan o cuáles sean sus puntos: el contador es único.

Este tipo de atributo se usa cuando algo pertenece conceptualmente a la clase como conjunto, no a cada objeto. Desde aquí la curiosidad lleva a campos como los métodos static, inicialización estática y patrones de diseño como Singleton o constantes globales, donde las clases juegan a ser “contenedores” más que “plantillas de objetos”.

Errores comunes

  • Usar static para guardar datos que deberían ser propios de cada objeto.
  • Acceder a un atributo estático usando una instancia en vez de la clase.

Métodos static en Java

Un método static es un método que pertenece a la clase, no a los objetos.
Se puede ejecutar sin crear ninguna instancia.

  • Se llama directamente desde la clase.
  • No puede usar this.
  • No puede acceder directamente a atributos no estáticos.
  • Ideal para lógica independiente del estado de los objetos.

Cuándo usarlo

  • Métodos de utilidad (cálculos, conversiones, validaciones).
  • Operaciones matemáticas o lógicas puras.
  • Métodos fábrica.
  • Acceso a recursos compartidos.
public class Conversor {
    public static double celsiusAFahrenheit(double c) {
        return (c * 9/5) + 32;
    }
}
double f = Conversor.celsiusAFahrenheit(20);
System.out.println(f); // 68.0

Diferencia clave frente a métodos normales

Un método normal trabaja sobre un objeto concreto.
Un método static trabaja sobre la idea de la clase.


Relación entre static y diseño de clases

  • Lo no estático representa el estado individual de cada objeto.
  • Lo estático representa el estado o comportamiento global de la clase.

Entender esta diferencia es fundamental para:

  • Diseñar bien las clases.
  • Evitar estado global innecesario.
  • Preparar el terreno para patrones de diseño.

Introducción al patrón Singleton

El patrón Singleton garantiza que una clase tenga una única instancia y proporciona un punto de acceso global a ella.

Por qué existe

Hay elementos del sistema que deben existir una sola vez:

  • Configuración global.
  • Logger.
  • Gestor de recursos.
  • Controladores centrales.

Características básicas

  • Constructor privado (no se puede usar new desde fuera).
  • Atributo static que guarda la única instancia.
  • Método static que devuelve esa instancia.

Qué problema resuelve

  • Crear múltiples objetos que representan lo mismo.
  • Inconsistencias de estado.
  • Accesos descontrolados a recursos compartidos.

Singleton y static: conexión directa

El patrón Singleton combina directamente los conceptos vistos:

  • Usa un atributo static para almacenar la instancia única.
  • Usa un método static como punto de acceso.
  • Refuerza la idea de que algunas cosas pertenecen a la clase, no a los objetos.

Ejemplo

  1. La clase se crea a sí misma por dentro.
  2. La clase guarda la única instancia en un atributo estático.
  3. Como el constructor es privado, nadie puede hacer new.
  4. Se accede usando un método static que devuelve siempre la misma instancia.

Un ejemplo:

public class Configuracion {

    // La única instancia
    private static Configuracion instancia;

    // Constructor privado para evitar new desde fuera
    private Configuracion() {
        // Inicialización
    }

    // Punto de acceso controlado
    public static Configuracion getInstancia() {
        if (instancia == null) {
            instancia = new Configuracion();
        }
        return instancia;
    }

    public void saludar() {
        System.out.println("Soy la única configuración.");
    }
}

Uso:

Configuracion c1 = Configuracion.getInstancia();
Configuracion c2 = Configuracion.getInstancia();

System.out.println(c1 == c2); // true

Ese true es la prueba de que ambos apuntan al mismo objeto.

Singleton = una clase que garantiza una sola instancia y un único punto de acceso.