Hello again
,
Last time
we discussed about different Factory Patter .
This time we
will learn about the Singleton Pattern.
THis
article is at CodePlex
Pattern
Name:
Singleton Pattern
Short
Description:
Class with only one single possible
instance
Usage:
Often used for objects that need to
provide global access with the constraint of only one single instance in the
application
Complexity:
1 / 5
UML
Class Diagram:
Explanation:
- There are multiple ways of implementing the Singleton
Pattern in C#. I am going to explain the most efficient approaches that
also provide thread safety.
- Note that in the first example the default constructor
is defined as private so that it is not possible to instantiate the object
from the outside. The class is also marked as sealed which means that
inheritance is not allowed for it.
- The internally instantiated object is stored in a
private variable that is marked as static. The public static property GetInstance
is used to allow access to this object. It contains the business logic
that assures that only a single instance can ever exist.
- To achieve this behavior a lock strategy is used to
assure that only a single thread is allowed to do the null check and
create a new instance if it does not already exist.
- A test function DisplayConfiguration() was added to be
able to verify the class design.
public sealed class ConfigurationManager
{
private static ConfigurationManager instance;
private static object syncRoot = new Object();
private ConfigurationManager()
{
}
public static ConfigurationManager GetInstance
{
get
{
lock (syncRoot)
{
if (instance == null)
{
instance = new ConfigurationManager();
}
}
return instance;
}
}
public void DisplayConfiguration()
{
Console.WriteLine("Single instance object");
}
}
{
private static ConfigurationManager instance;
private static object syncRoot = new Object();
private ConfigurationManager()
{
}
public static ConfigurationManager GetInstance
{
get
{
lock (syncRoot)
{
if (instance == null)
{
instance = new ConfigurationManager();
}
}
return instance;
}
}
public void DisplayConfiguration()
{
Console.WriteLine("Single instance object");
}
}
- Note that in the second example the default constructor
is also defined as private so that it is not possible to instantiate the
object from the outside. The class is also marked as sealed which means
that inheritance is not allowed for it.
- This time a private nested class is used to provide
access to the instance that must only exist once in the application.
- This nested class has a static default constructor and
an internal static read-only instance of the object. Only the container
class has access to the instance which will due to the software design
(auto-instantiated and marked as read-only) only exist once.
- A test function DisplayRules() was added to be able to
verify the class design.
- I recommend using this example as your default approach
for your Singleton implementations since there is no locking in it which
makes it more efficient in terms of performance.
public sealed class BusinessRulesManager
{
private BusinessRulesManager()
{
}
public static BusinessRulesManager GetInstance
{
get
{
return BusinessRulesManagerImpl.instance;
}
}
public void DisplayRules()
{
Console.WriteLine("Single instance object");
}
private class BusinessRulesManagerImpl
{
static BusinessRulesManagerImpl()
{
}
internal static readonly BusinessRulesManager instance = new BusinessRulesManager();
}
}
{
private BusinessRulesManager()
{
}
public static BusinessRulesManager GetInstance
{
get
{
return BusinessRulesManagerImpl.instance;
}
}
public void DisplayRules()
{
Console.WriteLine("Single instance object");
}
private class BusinessRulesManagerImpl
{
static BusinessRulesManagerImpl()
{
}
internal static readonly BusinessRulesManager instance = new BusinessRulesManager();
}
}
- In the last step we add some code to test the software
design and the Singleton implementation.
private static void Singleton()
{
var configurationManager = ConfigurationManager.GetInstance;
configurationManager.DisplayConfiguration();
var businessRulesManager = BusinessRulesManager.GetInstance;
businessRulesManager.DisplayRules();
Console.ReadKey();
}
{
var configurationManager = ConfigurationManager.GetInstance;
configurationManager.DisplayConfiguration();
var businessRulesManager = BusinessRulesManager.GetInstance;
businessRulesManager.DisplayRules();
Console.ReadKey();
}
- When running the example you can see that everything is
working as expected (it is however not as simple to test that there really
is just one single instance, you just have to believe in the correct
software design).
Regards
Amey
Start where you are. Use what you have. Do what you can.
![image_thumb2_thumb[2]](file:///C:/Users/ADMINI~1/AppData/Local/Temp/msohtmlclip1/01/clip_image002.gif)
![image_thumb_thumb[1]](file:///C:/Users/ADMINI~1/AppData/Local/Temp/msohtmlclip1/01/clip_image003.gif)
No comments:
Post a Comment