Difference between revisions of "Singleton"

From CDOT Wiki
Jump to: navigation, search
(Sample Code)
 
Line 15: Line 15:
 
Singleton pattern in C#:
 
Singleton pattern in C#:
 
<pre>
 
<pre>
class Singleton
+
// Singleton pattern -- Real World example 
 +
 
 +
using System;
 +
using System.Collections;
 +
using System.Threading;
 +
 
 +
namespace DoFactory.GangOfFour.Singleton.RealWorld
 
{
 
{
   private static Singleton instance;
+
    
 +
  // MainApp test application
  
   // Note: Constructor is 'protected'
+
   class MainApp
  protected Singleton()
 
 
   {
 
   {
 +
    static void Main()
 +
    {
 +
      LoadBalancer b1 = LoadBalancer.GetLoadBalancer();
 +
      LoadBalancer b2 = LoadBalancer.GetLoadBalancer();
 +
      LoadBalancer b3 = LoadBalancer.GetLoadBalancer();
 +
      LoadBalancer b4 = LoadBalancer.GetLoadBalancer();
 +
 +
      // Same instance?
 +
      if (b1 == b2 && b2 == b3 && b3 == b4)
 +
      {
 +
        Console.WriteLine("Same instance\n");
 +
      }
 +
 +
      // All are the same instance -- use b1 arbitrarily
 +
      // Load balance 15 server requests
 +
      for (int i = 0; i < 15; i++)
 +
      {
 +
        Console.WriteLine(b1.Server);
 +
      }
 +
 +
      // Wait for user
 +
      Console.Read();   
 +
    }
 
   }
 
   }
  
   public static Singleton Instance()
+
   // "Singleton"
 +
 
 +
  class LoadBalancer
 
   {
 
   {
     // Use 'Lazy initialization'
+
    private static LoadBalancer instance;
     if (instance == null)
+
    private ArrayList servers = new ArrayList();
 +
 
 +
    private Random random = new Random();
 +
 
 +
     // Lock synchronization object
 +
     private static object syncLock = new object();
 +
 
 +
    // Constructor (protected)
 +
    protected LoadBalancer()  
 
     {
 
     {
       instance = new Singleton();
+
       // List of available servers
 +
      servers.Add("ServerI");
 +
      servers.Add("ServerII");
 +
      servers.Add("ServerIII");
 +
      servers.Add("ServerIV");
 +
      servers.Add("ServerV");
 +
    }
 +
 
 +
    public static LoadBalancer GetLoadBalancer()
 +
    {
 +
      // Support multithreaded applications through
 +
      // 'Double checked locking' pattern which (once
 +
      // the instance exists) avoids locking each
 +
      // time the method is invoked
 +
      if (instance == null)
 +
      {
 +
        lock (syncLock)
 +
        {
 +
          if (instance == null)
 +
          {
 +
            instance = new LoadBalancer();
 +
          }
 +
        }
 +
      }
 +
 
 +
      return instance;
 
     }
 
     }
  
     return instance;
+
     // Simple, but effective random load balancer
  }
+
 
}
+
    public string Server
</pre>
+
    {
Singleton pattern in PHP 5:
+
      get
<pre>
+
      {
<?php
+
        int r = random.Next(servers.Count);
class Singleton {
+
        return servers[r].ToString();
  // object instance
+
       }
  static $instance;
 
 
 
  private function __construct() {}
 
  private function __clone() {}
 
 
 
  public static function getInstance() {
 
    if (!Singleton::$instance instanceof self) {
 
       Singleton::$instance = new self();
 
 
     }
 
     }
    return Singleton::$instance;
 
 
   }
 
   }
}
+
}  
?>
 
 
</pre>
 
</pre>
  

Latest revision as of 10:52, 2 April 2007

Go Back Pattern List

Introduction

Singleton pattern Ensure a class only has one instance, and provide a global point of access to it. This is useful when exactly one object is needed to coordinate actions across the system.

Implementation

  • Singleton pattern is implemented by creating a class with a method that creates a new instance of the object if one does not exist.
  • If an instance already exists, it simply returns a reference to that object.
  • To make sure that the object cannot be instantiated any other way, the constructor is made either private or protected.

UML Diagram

Singleton UML.png

Sample Code

Singleton pattern in C#:

// Singleton pattern -- Real World example  

using System;
using System.Collections;
using System.Threading;

namespace DoFactory.GangOfFour.Singleton.RealWorld
{
  
  // MainApp test application 

  class MainApp
  {
    static void Main()
    {
      LoadBalancer b1 = LoadBalancer.GetLoadBalancer();
      LoadBalancer b2 = LoadBalancer.GetLoadBalancer();
      LoadBalancer b3 = LoadBalancer.GetLoadBalancer();
      LoadBalancer b4 = LoadBalancer.GetLoadBalancer();

      // Same instance? 
      if (b1 == b2 && b2 == b3 && b3 == b4)
      {
        Console.WriteLine("Same instance\n");
      }

      // All are the same instance -- use b1 arbitrarily 
      // Load balance 15 server requests 
      for (int i = 0; i < 15; i++)
      {
        Console.WriteLine(b1.Server);
      }

      // Wait for user 
      Console.Read();    
    }
  }

  // "Singleton" 

  class LoadBalancer
  {
    private static LoadBalancer instance;
    private ArrayList servers = new ArrayList();

    private Random random = new Random();

    // Lock synchronization object 
    private static object syncLock = new object();

    // Constructor (protected) 
    protected LoadBalancer() 
    {
      // List of available servers 
      servers.Add("ServerI");
      servers.Add("ServerII");
      servers.Add("ServerIII");
      servers.Add("ServerIV");
      servers.Add("ServerV");
    }

    public static LoadBalancer GetLoadBalancer()
    {
      // Support multithreaded applications through 
      // 'Double checked locking' pattern which (once 
      // the instance exists) avoids locking each 
      // time the method is invoked 
      if (instance == null)
      {
        lock (syncLock)
        {
          if (instance == null)
          {
            instance = new LoadBalancer();
          }
        }
      }

      return instance;
    }

    // Simple, but effective random load balancer 

    public string Server
    {
      get
      {
        int r = random.Next(servers.Count);
        return servers[r].ToString();
      }
    }
  }
} 

References

http://en.wikipedia.org/wiki/Singleton_pattern
http://www.dofactory.com/Patterns/PatternSingleton.aspx

Go Back Pattern List