Command (Polecenie) – należy do czynnościowego wzorca projektowego

Wzorzec który ostatnio mi się spodobał. Kiedyś w pisanym edytorze rozkazy do wykonania były kolejkowane jako ENUM’y w kolejce rozkazów do wykonania. Ten wzorzec zapewnia jednak większą elastyczność poprzez:

  • rozdzielenie zależności pomiędzy nadawcą i odbiorcą komunikatu
  • możliwość dodanie operacji undo oraz zapamiętania stanu obiektów przed wykonaniem polecenia
  • zastosowania rozkazów złożonych „wzorzec Kompozycji”
  • mogą sposób wykonania polecenia uzależniać od typu odbiorcy albo nadawcy
  • zastosowanie polimorfizmu pozwala na rozbudowywanie poleceń bez konieczności zmiany struktury systemu

Wadą tego wzorca jest konieczność utworzenia większej ilości obiektów co wiąże się z większym zużyciem pamięci

Wzorzec składa się z:

  • Interfejsu polecenia – definiuje on operacja do wykonania, w najprostszej postaci składa się z jednej metody publicznej
  • Obiektu polecenia – konkretny obiekt realizujący dane polecenie
  • Klient lub grupa klientów – obiekt lub więcej obiektów na którym dane polecenie będzie wykonywać operacje
  • Nadawca – obiekt tworzący polecenia i dodający do kolejki lub przekazujący do odbiorcy
  • Odbiorca – obiekt pobierający polecenia i wykonujący je

Diagram wzorca „Command”:

Design Pattern - Command

Przykładowa implementacja:

package pl.shad.net.blog;

import java.util.ArrayList;

//Interfejs wzorca Command
interface CommandInterface{
    void run();
}

//Klasy realizujące poszczególne rozkazy
class Command1 implements CommandInterface{
    @Override
    public void run(){
        System.out.println("Execute command 1 ...");
    }
}

class Command2 implements CommandInterface{
    @Override
    public void run(){
        System.out.println("Execute command 2 ...");
    }
}

class Command3 implements CommandInterface{
    @Override
    public void run(){
        System.out.println("Execute command 3 ...");
    }
}

//
// Test wzorca Command
// - dodanie rozkazów do kolejki
// - wywolanie rozkazów z kolejki
//
public class DesignPatternsCommand{

    ArrayList < CommandInterface > commandQueue = new ArrayList <>();

    public static void main(String[] args){

        DesignPatternsCommand ds = new DesignPatternsCommand();
        ds.test();
    }

    private void test(){

        System.out.println("Add commands to queue ...");

        commandQueue.add(new Command1());
        commandQueue.add(new Command2());
        commandQueue.add(new Command1());
        commandQueue.add(new Command3());
        commandQueue.add(new Command1());

        System.out.println("Execute commands from queue ...");

        for (CommandInterface command : commandQueue){
            if (command instanceof CommandInterface){
                command.run();
            }
        }
    }
}