Menu
Coddy logo textTech

Patrón Strategy

Parte de la sección Programación Orientada a Objetos del Journey de Java de Coddy — lección 69 de 87.

El Patrón Strategy es un patrón de diseño de comportamiento que permite definir una familia de algoritmos, encapsular cada uno en su propia clase y hacerlos intercambiables. En lugar de codificar de forma rígida un comportamiento específico, puedes intercambiar algoritmos en tiempo de ejecución sin cambiar el código que los utiliza.

Imagine un sistema de pago que admita múltiples métodos de pago. Sin el Patrón Strategy, terminaría con una lógica condicional desordenada. Con él, cada método de pago se convierte en su propia estrategia:

interface PaymentStrategy {
    void pay(int amount);
}

class CreditCardPayment implements PaymentStrategy {
    public void pay(int amount) {
        System.out.println("Paid " + amount + " via Credit Card");
    }
}

class PayPalPayment implements PaymentStrategy {
    public void pay(int amount) {
        System.out.println("Paid " + amount + " via PayPal");
    }
}

La clase context mantiene una referencia a una estrategia y le delega el trabajo. La clave es que el contexto no sabe qué estrategia concreta está utilizando; solo conoce la interfaz:

class ShoppingCart {
    private PaymentStrategy paymentStrategy;
    
    public void setPaymentStrategy(PaymentStrategy strategy) {
        this.paymentStrategy = strategy;
    }
    
    public void checkout(int amount) {
        paymentStrategy.pay(amount);
    }
}

Ahora puedes cambiar el comportamiento del pago dinámicamente:

ShoppingCart cart = new ShoppingCart();

cart.setPaymentStrategy(new CreditCardPayment());
cart.checkout(100);  // Pagado 100 mediante tarjeta de crédito

cart.setPaymentStrategy(new PayPalPayment());
cart.checkout(50);   // Pagado 50 mediante PayPal

El Patrón Strategy brilla cuando tienes múltiples formas de realizar una acción y quieres cambiar entre ellas fácilmente. Agregar un nuevo método de pago simplemente significa crear una nueva clase que implemente PaymentStrategy—no se requieren cambios en el código existente.

challenge icon

Desafío

Fácil

¡Vamos a construir un sistema de formateo de texto utilizando el Patrón Strategy! Crearás un sistema donde diferentes estrategias de formateo se pueden intercambiar en tiempo de ejecución para transformar el texto de varias maneras—perfecto para una aplicación que necesita soportar múltiples formatos de salida.

Organizarás tu código en cuatro archivos:

  • TextFormatter.java: Define la interfaz TextFormatter que implementarán todas las estrategias de formateo. Debe declarar un único método String format(String text) que recibe una cadena y devuelve la versión formateada.
  • Formatters.java: Crea tres estrategias concretas que implementen tu interfaz TextFormatter:

    UpperCaseFormatter - transforma el texto a letras mayúsculas.

    LowerCaseFormatter - transforma el texto a letras minúsculas.

    TitleCaseFormatter - pone en mayúscula la primera letra de cada palabra mientras que el resto queda en minúscula. Las palabras están separadas por espacios.

  • TextEditor.java: Crea la clase de contexto que utiliza una estrategia de formateo. Tu TextEditor debe tener:

    Un campo privado para mantener la estrategia TextFormatter actual.

    Un método setFormatter(TextFormatter formatter) que cambia la estrategia de formateo activa.

    Un método publishText(String text) que aplica el formateador actual al texto e imprime Published: [formatted text]. Si no se ha establecido ningún formateador, debe imprimir Published: [original text] sin cambios.

  • Main.java: ¡Une tu sistema de estrategias! Recibirás dos entradas: el texto a formatear (String) y el estilo de formateo (String: "upper", "lower", o "title").

    Crea un TextEditor y primero llama a publishText con tu texto de entrada antes de establecer cualquier formateador (demostrando el comportamiento por defecto).

    Luego, basándote en la entrada del estilo, establece la estrategia de formateador apropiada y llama a publishText de nuevo con el mismo texto para mostrar el resultado formateado.

Recibirás dos entradas en orden: el texto a formatear (String) y el estilo de formateo (String).

Por ejemplo, con las entradas hello world y title, tu salida sería:

Published: hello world
Published: Hello World

¡Observa cómo el TextEditor no sabe nada sobre la lógica de formateo específica—simplemente delega en cualquier estrategia que esté establecida actualmente! ¡Esto hace que sea trivial añadir nuevos estilos de formateo sin tocar el código del editor!

Hoja de referencia

El Patrón Strategy es un patrón de diseño de comportamiento que define una familia de algoritmos, encapsula cada uno en su propia clase y los hace intercambiables. Permite intercambiar algoritmos en tiempo de ejecución sin cambiar el código que los utiliza.

Componentes Clave

Interfaz Strategy: Define la interfaz común para todas las estrategias concretas.

interface PaymentStrategy {
    void pay(int amount);
}

Estrategias Concretas: Implementan la interfaz de estrategia con algoritmos específicos.

class CreditCardPayment implements PaymentStrategy {
    public void pay(int amount) {
        System.out.println("Paid " + amount + " via Credit Card");
    }
}

class PayPalPayment implements PaymentStrategy {
    public void pay(int amount) {
        System.out.println("Paid " + amount + " via PayPal");
    }
}

Clase Contexto: Mantiene una referencia a una estrategia y le delega el trabajo. El contexto solo conoce la interfaz, no la implementación concreta.

class ShoppingCart {
    private PaymentStrategy paymentStrategy;
    
    public void setPaymentStrategy(PaymentStrategy strategy) {
        this.paymentStrategy = strategy;
    }
    
    public void checkout(int amount) {
        paymentStrategy.pay(amount);
    }
}

Uso

Las estrategias se pueden cambiar dinámicamente en tiempo de ejecución:

ShoppingCart cart = new ShoppingCart();

cart.setPaymentStrategy(new CreditCardPayment());
cart.checkout(100);  // Pagado 100 a través de Tarjeta de Crédito

cart.setPaymentStrategy(new PayPalPayment());
cart.checkout(50);   // Pagado 50 a través de PayPal

Beneficios

El Patrón Strategy es ideal cuando se tienen múltiples formas de realizar una acción y se desea cambiar entre ellas fácilmente. Añadir una nueva estrategia simplemente significa crear una nueva clase que implemente la interfaz de estrategia; no se requieren cambios en el código existente.

Pruébalo tú mismo

import java.util.Scanner;

class Main {
    public static void main(String[] args) {
        Scanner scanner = new Scanner(System.in);
        String text = scanner.nextLine();
        String style = scanner.nextLine();
        
        // TODO: Crear una instancia de TextEditor
        
        // TODO: Llamar a publishText con el texto de entrada (antes de configurar cualquier formateador)
        
        // TODO: Basado en la entrada de estilo ("upper", "lower" o "title"),
        // configurar el formateador apropiado y llamar a publishText nuevamente
        
    }
}
quiz iconPonte a prueba

Esta lección incluye un breve cuestionario. Empieza la lección para responderlo y registrar tu progreso.

Todas las lecciones de Programación Orientada a Objetos