Al igual que los artículos anteriores , analicemos un problema de diseño para comprender el patrón de comando. Supongamos que está construyendo un sistema de automatización del hogar. Hay un control remoto programable que se puede usar para encender y apagar varios elementos en su hogar, como luces, estéreo, aire acondicionado, etc. Se parece a esto.
Puede hacerlo con declaraciones if-else simples como
if (buttonPressed == button1) lights.on()
Pero debemos tener en cuenta que encender algunos dispositivos como el estéreo consta de muchos pasos, como configurar cd, volumen, etc. También podemos reasignar un botón para hacer otra cosa. Al usar if-else simple, estamos codificando para la implementación en lugar de la interfaz. También hay un acoplamiento estrecho.
Entonces, lo que queremos lograr es un diseño que proporcione un acoplamiento flexible y que el control remoto no tenga mucha información sobre un dispositivo en particular. El patrón de comando nos ayuda a hacer eso.
Definición: el patrón de comando encapsula una solicitud como un objeto, lo que nos permite parametrizar otros objetos con diferentes requests, requests de cola o registro y admitir operaciones que se pueden deshacer.
La definición es un poco confusa al principio, pero analicemos paso a paso. En analogía con nuestro problema anterior, el control remoto es el cliente y el estéreo, las luces, etc. son los receptores. En el patrón de comando, hay un objeto de comando que encapsula una solicitud al vincular un conjunto de acciones en un receptor específico. Lo hace exponiendo solo un método de ejecución() que hace que se invoquen algunas acciones en el receptor.
Parametrizar otros objetos con diferentes requests en nuestra analogía significa que el botón que se usa para encender las luces se puede usar más tarde para encender el estéreo o tal vez para abrir la puerta del garaje.
poner en cola o registrar requests, y admitir operaciones que se pueden deshacer significa que la operación Ejecutar del Comando puede almacenar el estado para revertir sus efectos en el Comando mismo. El comando puede tener una operación unExecute agregada que revierte los efectos de una llamada anterior para ejecutar. También puede admitir cambios de registro para que puedan volver a aplicarse en caso de un bloqueo del sistema.
A continuación se muestra la implementación de Java del ejemplo de control remoto mencionado anteriormente:
Java
// A simple Java program to demonstrate // implementation of Command Pattern using // a remote control example. // An interface for command interface Command { public void execute(); } // Light class and its corresponding command // classes class Light { public void on() { System.out.println("Light is on"); } public void off() { System.out.println("Light is off"); } } class LightOnCommand implements Command { Light light; // The constructor is passed the light it // is going to control. public LightOnCommand(Light light) { this.light = light; } public void execute() { light.on(); } } class LightOffCommand implements Command { Light light; public LightOffCommand(Light light) { this.light = light; } public void execute() { light.off(); } } // Stereo and its command classes class Stereo { public void on() { System.out.println("Stereo is on"); } public void off() { System.out.println("Stereo is off"); } public void setCD() { System.out.println("Stereo is set " + "for CD input"); } public void setDVD() { System.out.println("Stereo is set"+ " for DVD input"); } public void setRadio() { System.out.println("Stereo is set" + " for Radio"); } public void setVolume(int volume) { // code to set the volume System.out.println("Stereo volume set" + " to " + volume); } } class StereoOffCommand implements Command { Stereo stereo; public StereoOffCommand(Stereo stereo) { this.stereo = stereo; } public void execute() { stereo.off(); } } class StereoOnWithCDCommand implements Command { Stereo stereo; public StereoOnWithCDCommand(Stereo stereo) { this.stereo = stereo; } public void execute() { stereo.on(); stereo.setCD(); stereo.setVolume(11); } } // A Simple remote control with one button class SimpleRemoteControl { Command slot; // only one button public SimpleRemoteControl() { } public void setCommand(Command command) { // set the command the remote will // execute slot = command; } public void buttonWasPressed() { slot.execute(); } } // Driver class class RemoteControlTest { public static void main(String[] args) { SimpleRemoteControl remote = new SimpleRemoteControl(); Light light = new Light(); Stereo stereo = new Stereo(); // we can change command dynamically remote.setCommand(new LightOnCommand(light)); remote.buttonWasPressed(); remote.setCommand(new StereoOnWithCDCommand(stereo)); remote.buttonWasPressed(); remote.setCommand(new StereoOffCommand(stereo)); remote.buttonWasPressed(); } }
Producción:
Light is on Stereo is on Stereo is set for CD input Stereo volume set to 11 Stereo is off
Tenga en cuenta que el control remoto no sabe nada acerca de encender el estéreo. Esa información está contenida en un objeto de comando separado. Esto reduce el acoplamiento entre ellos.
ventajas:
- Hace que nuestro código sea extensible ya que podemos agregar nuevos comandos sin cambiar el código existente.
- Reduce el acoplamiento entre el invocador y el receptor de un comando.
Desventajas:
- Aumento en el número de clases para cada comando individual
Lectura adicional: método de comando en Python
Referencias:
- Head First Design Patterns (libro)
- https://github.com/bethrobson/Head-First-Design-Patterns/tree/master/src/headfirst/designpatterns/command
Si Este artículo es una contribución de Sulabh Kumar . te gusta GeeksforGeeks y te gustaría contribuir, también puedes escribir un artículo y enviarlo por correo a review-team@geeksforgeeks.org. Vea su artículo que aparece en la página principal de GeeksforGeeks y ayude a otros Geeks.
Escriba comentarios si encuentra algo incorrecto o si desea compartir más información sobre el tema tratado anteriormente.
Publicación traducida automáticamente
Artículo escrito por GeeksforGeeks-1 y traducido por Barcelona Geeks. The original can be accessed here. Licence: CCBY-SA