|
|
Line 1: |
Line 1: |
| ==Introduction==
| | This page has been moved to [http://expertiza.csc.ncsu.edu/wiki/index.php/CSC/ECE_517_Fall_2011/ch4_4h_kp http://expertiza.csc.ncsu.edu/wiki/index.php/CSC/ECE_517_Fall_2011/ch4_4h_kp] |
| This wiki article discusses about some of the commonly used & easy to understand Desgin patterns[http://en.wikipedia.org/wiki/Design_pattern_(computer_science)] in the software industry. Specifically, we will be studying about the Singleton, Adapter, Command & Strategy patterns. | |
| | |
| ==Design Pattern==
| |
| | |
| ===Definition===
| |
| ===Examples===
| |
| | |
| ==Case Study==
| |
| ===Singleton===
| |
| [http://en.wikipedia.org/wiki/Singleton_pattern Singleton] is a design pattern which imposes a restriction on the class to instantiate exactly one object of that class.
| |
| | |
| ====Implementation====
| |
| *In Java, We can create a [http://en.wikipedia.org/wiki/Thread-safe thread-safe] & [http://en.wikipedia.org/wiki/Lazy_initialization lazy version] of Singleton as follows. The comments in the code help you understand the Lazy & thread-safe aspect of it.
| |
| <nowiki>
| |
| public class Singleton {
| |
| private static Singleton instance;
| |
|
| |
| private Singleton() {
| |
| //Do nothing. Initialize the object only when the first time getInstance() is called.
| |
| }
| |
|
| |
| public static synchronized Singleton getInstance() {
| |
| | |
| //The keyword "synchronized" makes it thread safe so that two threads invoking getInstance()
| |
| //at the same time cannot create two instances when a context switch happens so as to
| |
| //facilitate this scenario. In general this can happen even with 'n' threads invoking getInstance().
| |
| //"synchronized" keyword is used to eliminate such scenarios.
| |
| | |
| if (null == instance) {
| |
| instance = new Singleton();
| |
| }
| |
| return instance;
| |
| }
| |
| }
| |
| </nowiki>
| |
| | |
| | |
| *In Ruby, we can achieve singleton classes by mixing-in the 'Singleton' module as follows. Here, "SingletonClass" is the name of the singleton class that is being created.
| |
| <nowiki>
| |
| require 'singleton'
| |
| class SingletonClass
| |
| include Singleton
| |
| ...
| |
| end
| |
| </nowiki>
| |
| | |
| ====When should we use Singleton ? <ref>[http://stackoverflow.com/questions/228164/on-design-patterns-when-to-use-the-singleton When should we use Singleton ?]</ref> ====
| |
| There is a lot of criticism to the use of singleton pattern. So, how do we decide whether an object should be singleton or not ?
| |
| For an object to be considered as a singleton object, they must satisfy three requirements:
| |
| #controls concurrent access to a shared resource.
| |
| #access to the resource will be requested from multiple, disparate parts of the system.
| |
| #there can be only one object.
| |
| | |
| ====Applications====
| |
| ====Advantages====
| |
| *Singletons are often preferred to global variables as they don't pollute the global [http://en.wikipedia.org/wiki/Namespace namespace] with unnecessary variables & also can be instantiated only when needed unlike global variables which always consume resources.
| |
| | |
| ====Drawbacks====
| |
| *Introduces a global state into the application.
| |
| *Can make unit testing classes in isolation difficult.
| |
| Checkout the [http://www.youtube.com/watch?v=-FRm3VPhseI this] video from Misko Hevery which explains in detail when the usage of singletons is not exercised.<ref>[http://www.youtube.com/watch?v=-FRm3VPhseI Why Singletons are bad]</ref>
| |
| | |
| ===Adapter===
| |
| | |
| ===Command===
| |
| | |
| ===Strategy===
| |
| ====Definition====
| |
| "In computer programming, the strategy pattern is a design pattern, whereby algorithms can be selected at runtime. Formally speaking, the strategy pattern defines a family of algorithms, encapsulates each one, and makes them interchangeable. Strategy lets the algorithm vary independently from clients that use it." - Wikipedia <ref>[http://en.wikipedia.org/wiki/Strategy_pattern Stratey Pattern Wikipedia]</ref>
| |
| | |
| ====Example code for Strategy pattern====
| |
| Here we will see how strategy pattern can be used to sort a given list of real numbers using either BubbleSort() or QuickSort().
| |
| | |
| Below is an interface to describe the individual algorithms.
| |
| <nowiki>
| |
| public interface SortingInterface {
| |
| public void sort(double[] list);
| |
| }
| |
| </nowiki>
| |
| | |
| | |
| Now implement both the Quicksort & Bubblesort strategies.
| |
| <nowiki>
| |
| public class QuickSort implements SortingInterface {
| |
| //QuickSort will implement the sort() with the quicksort version.
| |
| public void sort(double[] list) {
| |
| //Do quick sort here
| |
| }
| |
| }
| |
| | |
| | |
| public class BubbleSort implements SortingInterface {
| |
|
| |
| //BubbleSort will implement the sort() with the bubblesort version.
| |
| public void sort(double[] list) {
| |
| | |
| | |
| //Do bubble sort here
| |
| }
| |
| }
| |
| </nowiki>
| |
| | |
| | |
| Now define a Strategy context that maintains a reference to a Strategy object(Bubblesort or Quicksort) and forwards client requests to that strategy.
| |
| | |
| <nowiki>
| |
| public class Context {
| |
| private SortingInterface algorithm = null;
| |
| | |
| public void sortGivenList(double[] list) {
| |
| algorithm.sort(list);
| |
| }
| |
| | |
| //Getter method for algorithm
| |
| public SortingInterface getAlgorithm() {
| |
| return algorithm;
| |
| }
| |
| | |
| //Setter method for algorithm
| |
| public void setAlgorithm(SortingInterface algorithm) {
| |
| this.algorithm = algorithm;
| |
| }
| |
| | |
| }
| |
| </nowiki>
| |
| | |
| | |
| Finally, the client picks one of the available strategies(Quicksort or Bubblesort) in the context and sorts the List according to that strategy as shown below.
| |
| <nowiki>
| |
| public class Client {
| |
| | |
| public static void main(String[] args) {
| |
|
| |
| //Here is the List
| |
| double[] list = {1,2.4,7.9,3.2,1.2,0.2,10.2,22.5,19.6,14,12,16,17};
| |
| | |
| //Now define the Context
| |
| Context context = new Context();
| |
| | |
| //Now pick your strategy i.e. Quicksort or Bubblesort
| |
| context.setAlgorithm(new BubbleSort());
| |
| | |
| ///Now, sort it using the strategy you picked
| |
| context.sortGivenList(list);
| |
|
| |
| }
| |
| </nowiki>
| |
| | |
| ====Applications====
| |
| *Sorting a list: where the strategy can be to choose the sorting algorithm itself (QuickSort, HeapSort, etc.) at runtime depending on the input data. <ref>[http://java-x.blogspot.com/2006/12/implementing-strategy-pattern-in-java.html Sorting a llist using Strategy pattern]</ref>
| |
| *[http://en.wikipedia.org/wiki/Layout_manager Layout Managers] in UI toolkits: where you can decide at runtime what layout is to be chosen for the GUI to be displayed.<ref>[http://stackoverflow.com/questions/370258/real-world-example-of-the-strategy-pattern Strategy Pattern Real world examples]</ref>
| |
| | |
| ====Differences between Command and Strategy Pattern====
| |
| *A Command Pattern encapsulates a single action/algorithm whereas the Strategy pattern provides us with a number of actions/algorithms which can be selected based on a number of factors.
| |
| *A Command Pattern object has a single method but with a generic signature whereas Strategy pattern may have as many different methods provided.
| |
| | |
| ==Conclusion==
| |
| | |
| ==References==
| |
| <references/>
| |
| | |
| ==External Links==
| |