CSC/ECE 517 Fall 2012/ch2b 2w40 sn

From Expertiza_Wiki
Revision as of 08:57, 18 November 2012 by Npatowa (talk | contribs)
Jump to navigation Jump to search

Introduction to Command Pattern

The command pattern is one of the most used behavioral design patterns. The main concept of the pattern is an object which can be used to represent and encapsulate all the information needed to call a method at a later time. This information includes the method name, the object that owns the method and values for the method parameters.

The command pattern has been often associated with these terms client, invoker and receiver. The client instantiates the command object and provides the information required to call the method at a later time. The invoker decides when the method should be called. The receiver is an instance of the class that contains the method's code.

The intent of the Command pattern can be listed as:

  1. encapsulate a request in an object
  2. allows the parametrization of clients with different requests
  3. allows saving the requests in a queue

A Java Example

As the figure above suggests the integral parts of the command pattern are the client,invoker and the receiver.The command part is split into two parts-the interface and the concrete command. The examples are explored more in the below example. This is the command interface which contains the skeleton code of the command pattern containing exactly one method called execute.

//Command
public interface Command
{
    public void execute();
}
//Concrete Command
public class LightOnCommand implements Command
{
    //reference to the light
    Light light;
    
    public LightOnCommand(Light light)
    {
        this.light = light;
    }
    
    public void execute()
    {
        light.switchOn();
    }
    
}
 
 //Concrete Command
public class LightOffCommand implementsCommand
{
    //reference to the light
    Light light;
    
    public LightOffCommand(Light light)
    {
        this.light = light;
    }
    
    public void execute()
    {
        light.switchOff();
    }
    
}

LightOnCommand and LightOffCommand represents the concrete command classes that the client shall use.

Light is the receiver class which contains the commands to be executed.

//Receiver
public class Light
{
   private boolean on;
  
   public void switchOn()
   {
      on = true;
   }
  
   public void switchOff()
   {
      on = false;
   }
  
}

The invoker is the one which actually which calls the execute method of the command class. This also has a accessor method which sets the current command to be executed.

//Invoker
public class RemoteControl
{
    private Command command;

    public void setCommand(Command command)
    {
        this.command = command;
    }
    
   
    public void pressButton()
    {
        command.execute();
    }
    
}

And finally there is the Client class which will use the commands to switch the lights on and off.

//Client
public class Client
{
    public static void main(String[] args)
    {
        RemoteControl control = new RemoteControl();
        
        Light light = new Light();
        
        Command lightsOn = new LightsOnCommand(light);
        Command lightsOff = new LightsOffCommand(light);
        
        //switch on
        control.setCommand(lightsOn);
        control.pressButton();
        
        //switch off
        control.setCommand(lightsOff);
        control.pressButton();
    
    }

}

Real life applications

The command pattern can be used when the following things are desired:

  1. Specify,queue and execute requests at different times.
  2. To support operations like Undo,Redo.
  3. Support Logging changes so that they can be reapplied in case of a system crash.If the command interface is extended to include the load and store operations, a persistent history of changes can be kept.
  4. These can also be applied to transactions. They have a common interface so all the transactions can be invoked in the same way. It is also helpful to rollback transaction if something goes wrong.
  5. It is also used for implementing GUI objects. In addition to the ability to perform the desired command, an Action may have an associated icon, keyboard shortcut, tooltip text, and so on.

For an additional list of applications users can read this [1].

Chain of Responsibility

Chain-of-responsibility pattern is another behavioral design pattern consisting of a source of command objects and a series of processing objects. Processing objects contain logic that defines the types of command objects that it can handle; the rest are passed to the next processing object in the chain. The basic intent of this pattern is to chain the receiving objects and pass the request along the chain until an object handles it. This pattern promotes decoupling between senders and receivers by giving multiple objects a chance to handle a request. The request gets passed along a chain of objects until one of them handles it. More information can be handled from here [2].

Example of Chain of Responsibility

The above figure helps to understand the workings of Chain of Responsibility pattern.The example given in [3] has been described below.

//Interface
public interface Chain {
 
  public abstract void setNext(Chain nextInChain);
  public abstract void process(Number request);
}
//Receiver
public class Number {
  private int number;
 
  public Number(int number) {
    this.number = number;
  }
 
  public int getNumber() {
    return number;
  }
 
}
//Concrete Handler1
public class NegativeProcessor implements Chain {
 
  private Chain nextInChain;
 
  public void setNext(Chain c) {
    nextInChain = c;
  }
 
  public void process(Number request) {
    if (request.getNumber() < 0) {
      System.out.println("NegativeProcessor : " + request.getNumber());
    } else {
      nextInChain.process(request);
    }
  }
}
//Concrete Handler2
public class ZeroProcessor implements Chain {
 
  private Chain nextInChain;
 
  public void setNext(Chain c) {
    nextInChain = c;
  }
 
  public void process(Number request) {
    if (request.getNumber() == 0) {
      System.out.println("ZeroProcessor : " + request.getNumber());
    } else {
      nextInChain.process(request);
    }
  }
}
//Concrete Handler3
public class PositiveProcessor implements Chain {
 
  private Chain nextInChain;
 
  public void setNext(Chain c) {
    nextInChain = c;
  }
 
  public void process(Number request) {
    if (request.getNumber() > 0) {
      System.out.println("PositiveProcessor : " + request.getNumber());
    } else {
      nextInChain.process(request);
    }
  }
}
//Client
public class TestChain {
  public static void main(String[] args) {
    //configure Chain of Responsibility
    Chain c1 = new NegativeProcessor();
    Chain c2 = new ZeroProcessor();
    Chain c3 = new PositiveProcessor();
    c1.setNext(c2);
    c2.setNext(c3);
 
    //calling chain of responsibility
    c1.process(new Number(99));
    c1.process(new Number(-30));
    c1.process(new Number(0));
    c1.process(new Number(100));
  }
}

In the above example the Chain interface is implemented by three handlers which handles 3 different types of numbers-positive numbers,negative numbers and the number zero. The first in the chain is the negative number handler which sets the next handler as the zero handler which in turn sets the positive handler as the last component in the chain.The Number class acts as the receiver which has been explained in the Command pattern.The TestChain is the client.

Comparison with Command Pattern

  1. Both in Command and Chain of Responsibility pattern commands or actions are stored so that it can be later used.
  2. The Chain of Responsibility forwards requests along a chain of classes, but the Command pattern forwards a request only to a specific object.
  3. The main intent of both the patterns is to decouple senders and receivers.In case of Command pattern that is only one.

Real life applications

Chain of Responsibility is used in many applications:

  1. It is used often to handle exceptions inside kernel.There will be a chain of interrupt handlers and the request is passed on until somebody handles it.
  2. The pattern is used in windows systems to handle events generated from the keyboard or mouse.
  3. Single sign on security solutions for web applications. You might have a handler to check if the user is already authenticated, another handler to check for windows authentication, and a last handler to transfer the request to a logon page[4].


Memento

Comparison with Command Pattern

Real life applications

Strategy

Comparison with Command Pattern

Real life applications

Conclusion

Advantages and Disadvantages