Sei sulla pagina 1di 24

Exploring the Singleton Design Pattern

Introduction

In the course of developing software applications, repetitive patterns emerge as the application is developed. As whole
software systems are developed, many of these same patterns become evident at scale.

This concept of repetitive pattern is evident in other applications. One such application is automobile manufacturing. Many
different automobile models share the same sub-assemblies from the most basic components, such as light bulbs and
fasteners, to larger assemblies, such as chassis and engines.

In homebuilding, the repetitive pattern concept applies to screws and nails as well as to whole building electrical distribution
systems. Whether a team is assembled to create a new automobile or a new building design, it usually does not have to
ponder problems that were solved before. If a team assigned to design and build a house had to rethink and design every
single component of the house, the whole process would take much longer than it currently does. Design decisions such as
the height of a door or the function of a light switch are well understood. A house designer does not have to redesign and
reconstruct a different type of device to deliver and collect water in order to meet a requirement to supply hand washing
functionality to different parts of the house: a standard sink, as well as a standard interface of hot and cold water inputs and
drain water output, are well understood components of house construction. The repetitive pattern concept can be applied
over and over to nearly everything we surround ourselves with, including software.

The automobile and homebuilding examples help visualize some general abstract concepts in software design and
construction. The concept of well-defined general purpose units of functionality that are well understood is the motivation for
design patterns and the focus of two other design pattern articles, Exploring the Factory Design Pattern and Exploring the
Observer Design Pattern. These patterns cover nearly every aspect of object-oriented software design including object
creation, object interaction, and object lifetime. For the scope of this article, we are going to discuss the Singleton pattern,
which lives in a family of creational patterns.

Creational patterns dictate how and when objects get created. Many instances require special behavior that can only be
solved though creational techniques, rather than trying to force a desired behavior after an instance is created. One of the
best examples of this type of behavioral requirement is contained in the Singleton pattern. The Singleton pattern was
formally defined in the classic reference, Design Patterns: Elements of Reusable Software by Erich Gamma, Richard Helm,
Ralph Johnson, and John Vlissides (also known as the Gang of Four, or GoF). This pattern is one of the least complicated, as
well as most popular, in Design Patterns. However, as we will see, there can be problems with implementing this pattern.
This article attempts to examine the Singleton pattern from its beginning though various early implementations, as well as
how to best use it in Microsoft® .NET application development.

Singleton Pattern

The intent of the Singleton pattern as defined in Design Patterns is to "ensure a class has only one instance, and provide a
global point of access to it".

What problem does this solve, or put another way, what is our motivation to use it? In nearly every application, there is a
need to have an area from which to globally access and maintain some type of data. There are also cases in object-oriented
(OO) systems where there should be only one class, or a predefined number of instances of a class, running at any given
time. For example, when a class is being used to maintain an incremental counter, the simple counter class needs to keep
track of an integer value that is being used in multiple areas of an application. The class needs to be able to increment this
counter as well as return the current value. For this situation, the desired class behavior would be to have exactly one
instance of a class that maintains the integer and nothing more.
At first glance, one might be tempted to create an instance of a counter class as a just a static global variable. This is a
common technique but really only solves part of the problem; it solves the problem of global accessibility, but does nothing
to ensure that there is only one instance of the class running at any given time. The responsibility of having only one
instance of the class should fall on the class itself and not on the user of the class. The users of the class should always be
free from having to monitor and control the number of running instances of the class.

What is needed is a way to control how class instances are created and then ensure that only one gets created at any given
time. This would give us exactly the behavior we require and free a client from having to know any class details.

Logical Model

The model for a singleton is very straightforward. There is (usually) only one singleton instance. Clients access the singleton
instance through one well-known access point. The client in this case is an object that needs access to a sole instance of a
singleton. Figure 1 shows this relationship graphically.

Figure 1. Singleton pattern logical model

Physical Model

The physical model for the Singleton pattern is also very simple. However, there are several slightly different ways that
singletons have been implemented over time. Let's look at the original GoF singleton implementation. Figure 2 shows a UML
model of the original Singleton pattern as defined in Design Patterns.

Figure 2. Singleton pattern physical model from design patterns

What we see is a simple class diagram showing that there is a private static property of a singleton object as well as public
method Instance() that returns this same property. This is really the core of what makes a singleton. The other properties
and methods are there to show additional operations that may be allowed on the class. For the purpose of this discussion,
let's focus on the instance property and method.

Clients access any instance of a singleton only through the Instance method. How the instance gets created is not defined
here. What we also want to be able to do is control how and when an instance will get created. In OO development, special
object creation behavior is generally best handled in the constructor for a class. This case is no different. What we can do is
define when and how we construct a class instance and then keep any client from calling the constructor directly. This is the
approach always used for singleton construction. Let's look at the original example from Design Patterns. The C++ Singleton
Sample Implementation Code example shown below is generally considered the default implementation for a singleton. This
sample has been ported to many other programming languages and generally exists everywhere in very near this same
form.

C++ Singleton Sample Implementation Code


// Declaration

class Singleton {

public:

static Singleton* Instance();

protected:

Singleton();

private:

static Singleton* _instance;

// Implementation

Singleton* Singleton::_instance = 0;

Singleton* Singleton::Instance() {

if (_instance == 0) {

_instance = new Singleton;

return _instance;

Let’s examine this code for a moment. This simple class has one member variable and that is a pointer to itself. Notice that
the constructor is protected and that the only public method is the Instance method. In the implementation of the Instance
method, there is a control block (if) that checks to see if the member variable has been initialized, and if not creates a new
instance. This lazy initialization in the control block means that the Singleton instance is initialized, or created, only on the
first call to the Instance() method. For many applications, this approach works just fine. But, for multithreaded applications,
this approach proves to have a potentially hazardous side effect. If two threads manage to enter the control block at the
same time, two instances of the member variable could be created. To solve this, you might be tempted to merely place a
critical section around the control block in order to guarantee thread safety. If you do this, then all calls to the Instance
method would be serialized and could have a very negative impact on performance, depending on the application. It is for
this reason that another version of this pattern was created that uses something called a double-check mechanism. The next
code sample shows an example of a double-check lock using Java syntax.

Double-Check Lock Singleton Code Using Java Syntax

// C++ port to Java

class Singleton

public static Singleton Instance() {


if (_instance == null) {

synchronized (Class.forName("Singleton")) {

if (_instance == null) {

_instance = new Singleton();

return _instance;

protected Singleton() {}

private static Singleton _instance = null;

In the Double-Check Lock Singleton Code Using Java Syntax sample, we perform a direct port of the C++ code to Java code
in order to take advantage of the Java critical section block (synchronized). The major differences are that there are no
longer separate declaration and implementation sections, there are no pointer data types, and a new double-check
mechanism is in place. The double check occurs at the first IF block. If the member variable is null, then the execution enters
a critical section block where the member variable is double checked again. Only after passing this last test is the member
variable instantiated. The general thinking is that there is no way that two threads can create two instances of the class
using this technique. Also, since there is no thread blocking at the first check, most calls to this method would not get the
performance hit of having to enter the lock. Currently, this technique is widely used in many Java applications when
implementing a Singleton pattern. This technique is subtle but flawed. Some optimizing compilers can optimize out or reorder
the lazy initialization code and reintroduce the thread safety problem. For a more in-depth explanation, see "The Double-
Check Locking is Broken" Declaration.

Another way to attempt to fix this problem could be using the volatile keyword on the member variable declaration. This
should tell the compiler to not reorder the code and forgo optimization. Currently this is only a proposed memory model for a
JVM and does not solve the problem right now.

What is the best way to implement a singleton? It turns out, and not by accident, that the Microsoft .NET Framework has
addressed all of these issues, thus making it easier to implement a singleton without the adverse side effects we discussed
thus far. The .NET Framework, along with the C# language, allows us to port the preceding Java syntax to C# syntax by
substituting language keywords where appropriate. So the singleton code becomes the following:

Double-Check Lock in C#

// Port to C#

class Singleton

public static Singleton Instance() {

if (_instance == null) {

lock (typeof(Singleton)) {
if (_instance == null) {

_instance = new Singleton();

return _instance;

protected Singleton() {}

private static volatile Singleton _instance = null;

Here we have substituted the lock keyword to perform the critical section block, used the typeof operation, and added the
volatile keyword to ensure that there is no optimizer reordering of the code. Although this code is more or less a direct
port of the GoF Singleton pattern, it does achieve our goals and we get the behavior we want. This code also illustrates some
similarities as well as key differences in porting C++ to Java to C# code. However, as with any port of code, there are
usually some advantages of the target language or platform that may be lost in the porting process. What needs to happen is
a refactoring of the code in order to take advantage of the new target language or platform capabilities.

In each preceding code example, the original implementation for a singleton has undergone changes over time to address
issues that have been discovered with each new implementation of the pattern. Issues such as thread safety have required
changes to most implementations in order to account for the increasing demands, as well as evolutionary advances, in
modern applications. .NET provides an evolutionary step in application development. Many of the issues that had to be
accounted for in the preceding examples can be addressed at the Framework level and not at the implementation level.
Although the last example shows a working Singleton class using the .NET Framework and C#, this code can be greatly
simplified just by taking better advantage of the .NET Framework itself. The following sample uses .NET, is a minimal
Singleton class based loosely on the original GoF pattern, and still gets similar behavior.

.NET Singleton Example

// .NET Singleton

sealed class Singleton

private Singleton() {}

public static readonly Singleton Instance = new Singleton();

This version is dramatically simpler and more intuitive. Is it still a singleton? Let's look at what changed and then decide. We
modified the class itself to be sealed (non-inheritable), the lazy initialization code is removed, the Instance() method is
removed, and we modified the _instance variable extensively. The changes to the _instance variable include modifying the
access level to public, marking the variable as read-only, and initializing the variable at declaration time. Here we can
directly define the behavior we want and not be concerned with potential unwanted side effects of the implementation. So
what about the advantages of using lazy initialization and the hazards of multiple threads? All of the correct behaviors are
built into the .NET Framework. Let's take the first case, lazy initialization.
The main reasons for using lazy initialization initially were to get the behavior of having an instance created on only the first
call to the Instance() method, and because there was some openness in the C++ spec that did not define the exact
initialization order of static variables. To get desired singleton behavior in C++, a workaround that involved the use of lazy
initialization was necessary. What we really care about is that we get the instance created either on or just before the first
call to (in this case) the Instance property, and that we have a defined initialization order for static variables in a class. With
the .NET Framework, this is exactly the behavior we get. The Framework, during the JIT process, will initialize the static
property when (and only when) any method uses this static property. If the property is not used, then the instance is not
created. More precisely, what happens during JIT is that the class gets constructed and loaded when any static member of
the class is used by any caller. In this case the result is the same.

What about thread-safe initialization? The Framework addresses this too. The Framework internally guarantees thread safety
on static type initialization. In other words, in the example above, there is only one instance that would ever be created of
the Singleton class. Note also that the property field used to hold the instance of the class is called Instance. This choice
better illustrates that this value is an instance of the class as part of the discussion in this article. In the Framework itself
there are several classes that use this type of singleton, although the property name used is called Value instead. The
concept is exactly the same.

The rest of the changes to the class are meant to disallow sub-classing. Adding the sealed class modifier ensures that this
class will not be sub-classed. The GoF Singleton pattern details the issues with trying to subclass a singleton and it is
generally not a trivial matter. In most cases, it is very easy to develop a singleton without a parent class, and adding sub-
classing functionality adds a new level of complexity that is generally not needed anyway. As complexity increases, so does
the time required for testing, training, documenting, and so on. As a general rule, you never want to make any code more
complicated than it absolutely has to be.

Let's look at a how a singleton might be used. Using our original motivational concept of a counter, we can create a simple
Singleton counter class and show how we would use it. Figure 3 shows what the UML class description would look like.

Figure 3. UML Class Diagram

The corresponding class implementation code, as well as sample client usage, is shown below.

Sample Singleton Usage

sealed class SingletonCounter {

public static readonly SingletonCounter Instance =

new SingletonCounter();

private long Count = 0;

private SingletonCounter() {}

public long NextValue() {

return ++Count;

}
}

class SingletonClient {

[STAThread]

static void Main() {

for (int i=0; i<20; i++) {

Console.WriteLine("Next singleton value: {0}",

SingletonCounter.Instance.NextValue());

Here we created a Singleton class that maintains an incremental count with a type long. The client is a simple console
application that displays twenty values of the counter class. Although this sample is extremely simple, it does show how a
singleton could be implemented using .NET and then used in an application.

Conclusion

The Singleton design pattern is a very useful mechanism for providing a single point of object access in an object-oriented
application. Regardless of the implementation used, the pattern provides a commonly understood concept that can be easily
shared among design and development teams. However, as we have discovered, it is also important to note how different
these implementations can be and their potential side effects. The .NET Framework goes a long way to help an implementer
of a pattern design the type of functionality desired without having to deal with many of the side effects discussed in this
article. The validity of the pattern's original intent is proven when implemented properly.

Design patterns are very useful software design concepts that allow teams to focus on delivering the very best type of
applications, whatever they may be. The key is to make proper and effective use of design patterns, and the ongoing MSDN
series of articles on using design patterns with Microsoft .NET shows you how.

Exploring the Observer Design Pattern

Introduction

During the course of a given development project, it is not uncommon to use the concept of design patterns to address
certain problems relating to application design and architecture. However, the definition of design patterns is often difficult to
convey with any level of accuracy; as such, the concept warrants a brief examination of origin and history.

The origin of software design patterns is attributed to the work of Christopher Alexander. As a building architect, Alexander
noted the presence of common problems and related solutions within a given context. A design pattern, as Alexander termed
this problem/solution/context triad, enabled an architect to rapidly address issues in a uniform manner during building
design. First published twenty-five years ago, A Pattern Language: Towns, Buildings, Construction (Alexander et al, Oxford
University Press, 1977) introduced over 250 architectural design patterns and provided the basis for the inclusion of this
concept into the realm of software development.
In 1995, the software industry was first widely introduced to the design patterns as they directly related to building
applications. The four authors, Gamma, Helm, Johnson, and Vlissides (collectively known as the Gang of Four, or GoF),
intersected Alexander's design patterns with the burgeoning object-oriented software movement in their work, Design
Patterns: Elements of Reusable Object-Oriented Software (Addison-Wesley Pub Co, 1995). Based on their collective
experience and examination of existing object frameworks, the GoF provided 23 design patterns that examined common
problems and solutions encountered while designing and architecting applications. Following that publication, the concept of
design patterns has grown to encompass many problems and solutions encountered in the software domain. In fact, the
popularity of design patterns has given rise to the concept of anti-patterns, which are solutions that commonly worsen,
rather than solve, the problem at hand.

Why Design Patterns?

Although not a magic bullet (if such a thing exists), design patterns are an extremely powerful tool for a developer or
architect actively engaged in any development project. Design patterns ensure that common problems are addressed via
well-known and accepted solutions. The fundamental strength of patterns rests with the fact that most problems have likely
been encountered and solved by other individuals or development teams. As such, patterns provide a mechanism to share
workable solutions between developers and organizations. Regardless of where these patterns find their genesis, patterns
leverage this collective knowledge and experience. This ensures that correct code is developed more rapidly and reduces the
chance that a mistake will occur in design or implementation. In addition, design patterns offer common semantics between
members of an engineering team. As anyone who has been involved in a large-scale development project knows, having a
common set of design terms and principles is critical to the successful completion of the project. Best of all, design patterns—
if used judicially—can free up your time.

.NET Framework Patterns

Design patterns are not specifically tied to a given language or development platform (although the GoF limited their
examples to C++ and Smalltalk); the advent of the Microsoft .NET Framework provides a new opportunity and context to
examine design patterns. During the development of the Framework Class Library (FCL), Microsoft applied many of the same
patterns first introduced by the GoF in 1994. Due to the breadth of functionality exposed within the .NET Framework, entirely
new patterns were developed and introduced as well.

Over the course of this series, we will examine in detail several of the design patterns present within the FCL. The general
structure and benefits of each pattern will be considered, followed by an examination of the specific implementation present
in the FCL. Although most of the patterns we will examine find their genesis with the GoF, the .NET Framework offers a
number of innovative features for which little or no design guidance is presently available. Design patterns related to these
new features will be examined as well. Our investigation of design patterns begins with the Observer pattern.

Observer Pattern

One of the overriding principles of object-oriented development is the proper assignment of responsibility in the given
application. Each object in the system should focus on a discrete abstraction within the problem domain and nothing more.
In short, an object should do one thing and do it well. This approach ensures that a crisp boundary exists between objects,
enabling greater reuse and system maintainability.

One area where the proper separation of responsibility is of special importance is the interaction between the user interface
and the underlying business logic. During the development of an application, it is quite common for user interface
requirements to change rapidly without an associated impact on the rest of the application. In addition, it is also likely that
the business requirements will change without regard to the user interface. In many cases, both sets of requirements will
change, as anyone with substantial development experience well knows. Without the benefit of separation between the UI
and remainder of the application, modification of either portion may adversely impact the whole.
The need to provide a distinct boundary between the user interface and business logic is a common problem that spans
applications. As a result, a number of object-oriented frameworks developed since the inception of the GUI have supported
the wholesale separation of the user interface from the remainder of the application. Not surprisingly (well maybe a little),
most of these adopted a similar design pattern to provide this functionality. This pattern, commonly known as Observer, is
advantageous in creating a clear distinction between various objects in the system. In addition, it is not uncommon to find
this solution utilized within non-UI related segments of a framework or application as well. As with most other patterns, the
usefulness of the Observer pattern extends far beyond its original intent.

Logical Model

Although numerous variations of the Observer pattern exist, the basic premise of the pattern involves two actors, the
observer and the subject (those familiar with Smalltalk MVC will know these terms as the view and the model,
respectively). Within the context of a user interface, the observer is the object responsible for displaying data to the user.
The subject, on the other hand, represents a business abstraction that is modeled from the problem domain. As depicted in
Figure 1, a logical association exists between the observer and subject. When a change occurs in the subject object (e.g. the
modification of an instance variable), the observer observes this change and updates its display accordingly.

Figure 1. Observer and Subject Relationship

For example, suppose we have a simple application that tracks stock prices throughout the day. Within this application we
have a Stock class that models various stocks that are traded on the NASDAQ. This class contains an instance variable which
represents the current ask price, which fluctuates throughout the day. In order to display this information to the user, the
application uses a StockDisplay class that writes to stdout (standard output). Within this application, an instance of the
Stock class acts as the subject and an instance of the StockDisplay class as the observer. As the ask price changes over
the course of the trading day, the current ask price of the Stock instance changes as well (how it changes is not germane).
Since the StockDisplay instance is observing the Stock instance, these state changes (modification of the ask price) are
displayed to the user as they occur.

The use of this observation process ensures that a boundary exists between the Stock and StockDisplay classes. Suppose
that the requirements for the application change tomorrow, requiring the use of a form-based user interface. Enabling this
new functionality is a simple matter of constructing a new class, StockForm, to act as an observer. The Stock class would
not require any modification whatsoever. In fact, it would not even be aware that such a change was made. Likewise, if a
change in requirements dictated that the Stock class retrieved ask price information from another source (perhaps a Web
service rather than from a database), the StockDisplay class would not require modification. It simply continues to observe
the Stock, oblivious to any changes.

Physical Model

As with most solutions, the devil is in the details. The Observer pattern is no exception. Although the logical model states
that the observer observes the subject, this is actually a misnomer when implementing this pattern. More accurately, the
observer registers with the subject, expressing its interest in observing. When a state change occurs, the subject notifies
the observer of the change. When the observer no longer wishes to observe the subject, the observer unregisters from the
subject. These steps are known as observer registration, notification, and unregistration, respectively.
Most frameworks implement registration and notification via callbacks. The UML sequence diagrams shown in Figures 2, 3,
and 4 model the objects and method calls typically utilized with this approach. For those unfamiliar with sequence diagrams,
the topmost rectangular boxes represent objects while the arrows represent method calls.

Figure 2. Observer Registration

Figure 2 depicts the registration sequence. The observer invokes the Register method on the subject, passing itself as an
argument. Once the subject receives this reference, it must store it in order to notify the observer when a state change
occurs sometime in the future. Rather than storing the observer reference in an instance variable directly, most observer
implementations delegate this responsibility to a separate object, typically a container. Use of a container to store observer
instances provides important benefits that we will discuss shortly. With that in mind, the next action in the sequence is the
storage of the observer reference denoted by the invocation of the Add method on the container.

Figure 3. Observer Notification

Figure 3 highlights the notification sequence. When a state change occurs (AskPriceChanged), the subject retrieves all the
observers within the container by invoking the GetObservers method. The subject then enumerates through the retrieved
observers, calling the Notify method, which notifies the observer of the state change.
Figure 4. Observer Unregistration

Figure 4 shows the unregistration sequence. This sequence is performed when the observer no longer needs to observe the
subject. The observer calls the UnRegister method, passing itself as an argument. The subject then invokes the Remove
method on the container, ending the period of observation.

Returning to our stock application, let's examine the impact of the registration and notification process. During application
startup, an instance of the StockDisplay class registers with a Stock instance, passing itself as an argument to the
Register method. The Stock instance holds the reference to the StockDisplay instance (in a container). As the ask price
attribute changes, the Stock instance notifies the StockDisplay of the change, calling the Notify method. When the
application is shutting down, the StockDisplay instance unregisters from the Stock instance, calling the UnRegister
method, terminating the relationship between the two instances.

It is worth noting the benefits of utilizing a container, rather than an instance variable to store a reference to the observer.
Suppose that our requirements called for a real-time graph of ask prices over the course of the trading day, in addition to the
current user interface, StockDisplay. To that end, we create a new class named StockGraph which plots the ask price in
the y-axis and the time of day in the x-axis. When the application starts, it registers instances of both the StockDisplay and
StockGraph classes with a Stock instance. Since the subject is storing the observers in a container, as opposed to an
instance variable, this does not pose an issue. As the ask price changes, the Stock instance notifies both observer instances
in its container of the state change. As can be seen, the use of a container provides the flexibility to support multiple
observers per subject. This permits a subject to notify a potentially infinite number of observers of state changes, rather than
just one.

Although not a requirement, many frameworks provide a set of interfaces for observers and subjects to implement. As shown
in the C# and Microsoft® Visual Basic® .NET code samples below, the IObserver interface exposes one public method,
Notify. This interface is implemented by all classes which intend to act as observers. The IObservable interface,
implemented by all classes that intend to acts as subjects, exposes two methods, Register and UnRegister. These
interfaces generally take the form of abstract virtual classes or true interfaces, if the implementation language supports such
constructs. The utilization of these interfaces help to reduce the coupling between the observer and subject. Rather than a
tightly coupled association between the observer and subject classes, the IObserver and IObservable interfaces allow
operations independent of the implementation. Based on an examination of the interfaces, you will note that all methods are
typed to operate on the interface types, as opposed to concrete classes. This approach extends the benefits of the interface
programming model to the Observer pattern.

IObserver and IObservable interfaces (C#)

Copy Code
//interface the all observer classes should implement public interface IObserver { void Notify(object
anObject); }//IObserver //interface that all observable classes should implement public interface
IObservable { void Register(IObserver anObserver); void UnRegister(IObserver
anObserver); }//IObservable

IObserver and IObservable interfaces (Visual Basic .NET)

Copy Code
'interface the all observer classes should implement Public Interface IObserver Sub Notify(ByVal
anObject As Object) End Interface 'interface that all observable classes should implement Public
Interface IObservable Sub Register(ByVal anObserver As IObserver) Sub UnRegister(ByVal anObserver
As IObserver) End Interface
Turning again to our sample application, we know that the Stock class acts as the subject. As such, it would implement the
IObservable interface. Likewise, the StockDisplay class, implements the IObserver interface. Since all operations are
defined by the interface, rather than the specific class, the Stock class is not bound to StockDisplay class or vice versa.
This permits us to rapidly change the specific observer or subject implementation without impacting the rest of the
application (replacing the StockDisplay with a different observer or adding an additional observer instance).

In addition to these interfaces, it is not uncommon for a framework to provide a common base class for subjects to extend.
The extension of this base class reduces the effort required to support the Observer pattern. The base class implements the
IObservable interface, providing the required infrastructure to support the storage and notification of observer instances.
The C# and Visual Basic .NET code samples below outline such a base class named ObservableImpl. This class delegates
observer storage to a Hashtable instance in the Register and UnRegister methods, although potentially any container will
suffice (our example uses a Hashtable as the container for convenience, it only takes one method call to unregister a specific
observer instance). Also, note the addition of the NotifyObservers method. This method is used to notify the observers
stored within the Hashtable. When this method is invoked, the container is enumerated, calling the Notify method on the
observer instances.

ObservableImpl Class (C#)

Copy Code
//helper class that implements observable interface public class ObservableImpl:IObservable {
//container to store the observer instance (is not synchronized for this example) protected Hashtable
_observerContainer=new Hashtable(); //add the observer public void Register(IObserver anObserver){
_observerContainer.Add(anObserver,anObserver); }//Register //remove the observer public void
UnRegister(IObserver anObserver){ _observerContainer.Remove(anObserver); }//UnRegister
//common method to notify all the observers public void NotifyObservers(object anObject) {
//enumeration the observers and invoke their notify method foreach(IObserver anObserver in
_observerContainer.Keys)
{ anObserver.Notify(anObject); }//foreach }//NotifyObservers }//ObservableImpl

ObservableImpl Class (Visual Basic .NET)

Copy Code
'helper class that implements observable interface Public Class ObservableImpl Implements
IObservable 'container to store the observer instance (is not synchronized for this example) Dim
_observerContainer As Hashtable = New Hashtable() 'add the observer Public Sub Register(ByVal
anObserver As IObserver) Implements IObservable.Register _observerContainer.Add(anObserver,
anObserver) End Sub 'remove the observer Public Sub UnRegister(ByVal anObserver As IObserver)
Implements IObservable.UnRegister _observerContainer.Remove(anObserver) End Sub 'common
method to notify all the observers Public Sub NotifyObservers(ByVal anObject As Object) Dim
anObserver As IObserver 'enumerate the observers and invoke their notify method For Each
anObserver In _observerContainer.Keys anObserver.Notify(anObject) Next End Sub End Class
Our sample application can benefit from this base class infrastructure by modifying the Stock class to extend the
ObservableImpl class, rather than providing its own specific implementation of the IObservable interface. Since the
ObservableImpl class implements the IObservable interface, no change is required on the StockDisplay class. This
approach really simplifies the implementation of the Observer pattern, allowing multiple subjects to reuse the same
functionality while maintaining a loosely coupled relationship between the involved classes.

The Observer examples in C# and Visual Basic. NET below highlight the utilization of the IObservable and IObserver
interfaces, as well as the ObservableBase class in the context of our stock application. In addition to the Stock and
StockDisplay classes, this example uses MainClass to associate the observer and subject instances and modify the
AskPrice property of the Stock instance. This property is responsible for invoking the base class's NotifyObservers
method, which in turn notifies the instance of the associated state change.

Observer Example (C#)

Copy Code
//represents a stock in an application public class Stock:ObservableImpl { //instance variable for ask
price object _askPrice; //property for ask price public object AskPrice { set { _askPrice=value;
base.NotifyObservers(_askPrice); }//set }//AskPrice property }//Stock //represents the user interface in
the application public class StockDisplay:IObserver { public void Notify(object anObject)
{ Console.WriteLine("The new ask price is:" + anObject); }//Notify }//StockDisplay public class
MainClass{ public static void Main() { //create new display and stock instances StockDisplay
stockDisplay=new StockDisplay(); Stock stock=new Stock(); //register the grid
stock.Register(stockDisplay); //loop 100 times and modify the ask price for(int looper=0;looper <
100;looper++) { stock.AskPrice=looper; } //unregister the display
stock.UnRegister(stockDisplay); }//Main }//MainClass

Observer Example (Visual Basic .NET)

Copy Code
'Represents a stock in an application Public Class Stock Inherits ObservableImpl 'instance variable for
ask price Dim _askPrice As Object 'property for ask price Public WriteOnly Property AskPrice()
Set(ByVal value As Object) _askPrice = value NotifyObservers(_askPrice) End Set End Property End
Class 'represents the user interface in the application Public Class StockDisplay Implements IObserver
Public Sub Notify(ByVal anObject As Object) Implements IObserver.Notify Console.WriteLine("The new
ask price is:" & anObject) End Sub End Class Public Class MainClass Shared Sub Main() 'create new
grid and stock instances Dim stockDisplay As StockDisplay = New StockDisplay() Dim stock As Stock
= New Stock() Dim looper As Integer 'register the display stock.Register(stockDisplay) 'loop 100 times
and modify the ask price For looper = 0 To 100 stock.AskPrice = looper Next looper 'unregister the
display stock.UnRegister(stockDisplay) End Sub

Observer Pattern in the .NET Framework


Based on our understanding of the Observer pattern, let us now turn our attention to the use of this pattern within the .NET
Framework. Those of you with passing familiarity of the types exposed in the FCL will note that no IObserver,
IObservable, or ObservableImpl types are present in the Framework. The primary reason for their absence is the fact that
the CLR makes them obsolete after a fashion. Although you can certainly use these constructs in a .NET application, the
introduction of delegates and events provides a new and powerful means of implementing the Observer pattern without
developing specific types dedicated to support this pattern. In fact, as delegates and events are first class members of the
CLR, the foundation of this pattern is incorporated into the very core of the .NET Framework. As such, the FCL makes
extensive use of the Observer pattern throughout its structure.

Much has been written concerning the inner workings of delegates and events, thus there is no need for a similar accounting
here. It suffices to simply state that a delegate is the object-oriented (and type-safe) equivalent of a function pointer. A
delegate instance holds a reference to an instance or class method, permitting anonymous invocation of the bound method.
Events are special constructs declared on a class that help to expose state changes to interested objects at run time. An
event represents a formal abstraction (supported by the CLR and various compilers) of the registration, unregistration, and
notification methods we used previously to implement the Observer pattern. Delegates are registered with specific events at
run time. When the event is raised, all registered delegates are invoked so that they receive notification of the event. For a
more in-depth examination of delegates and events, see An Introduction to Delegates.

Prior to examining delegates and events in the context of the Observer pattern, it is worth noting that the various languages
supported by the CLR are free to expose the delegate and event mechanism as the language designer sees fit. As such, a
comprehensive study of these features across languages is not possible. For the purposes of the following discussion, we will
focus on the C# and Visual Basic .NET implementation of these features. If you are using a language other than C# or Visual
Basic .NET, please refer to the documentation for more information about how delegates and events are supported in your
language.

Using the terms defined by the Observer pattern, the class declaring the event is the subject. Unlike our previous use of the
IObservable interface and ObservableImpl class, the subject class is not required to implement a given interface or
extend a base class. The subject merely needs to expose an event; nothing more is required. The creation of the observer is
slightly more involved, yet infinitely more flexible (which we will discuss later). Rather than implementing the IObserver
interface and registering itself with the subject, an observer must create a specific delegate instance and register this
delegate with the subject's event. An observer must utilize a delegate instance of the type specified by the event declaration,
otherwise registration will fail. During the creation of this delegate instance, the observer passes the name of the method
(instance or static) that will be notified by the subject to the delegate. Once the delegate is bound to the method, it may be
registered with the subject's event. Likewise, this delegate may be unregistered from the event, as well. Subjects provide
notification to observers by invocation of the event.

If you are unfamiliar with delegates and events this may seem like a lot of work to implemented the Observer pattern,
especially compared to our previous use of the IObserver and IObservable interfaces. It is, however, a lot simpler than it
sounds and far easier to implement. The C# and Visual Basic .NET code samples below highlight the required class
modifications within our sample application to support delegates and events. Note the lack of any base classes or interfaces
used by the Stock or StockDisplay classes to the support the pattern.

Observer using delegates and events (C#)

Copy Code
public class Stock { //declare a delegate for the event public delegate void AskPriceDelegate(object
aPrice); //declare the event using the delegate public event AskPriceDelegate AskPriceChanged;
//instance variable for ask price object _askPrice; //property for ask price public object AskPrice { set
{ //set the instance variable _askPrice=value; //fire the event
AskPriceChanged(_askPrice); } }//AskPrice property }//Stock class //represents the user interface in
the application public class StockDisplay { public void AskPriceChanged(object aPrice)
{ Console.Write("The new ask price is:" + aPrice + "\r\n"); } }//StockDispslay class public class
MainClass { public static void Main(){ //create new display and stock instances StockDisplay
stockDisplay=new StockDisplay(); Stock stock=new Stock(); //create a new delegate instance and
bind it //to the observer's askpricechanged method Stock.AskPriceDelegate aDelegate=new
Stock.AskPriceDelegate(stockDisplay.AskPriceChanged); //add the delegate to the event
stock.AskPriceChanged+=aDelegate; //loop 100 times and modify the ask price for(int
looper=0;looper < 100;looper++) { stock.AskPrice=looper; } //remove the delegate from the event
stock.AskPriceChanged-=aDelegate; }//Main }//MainClass

Observer using delegates and events (Visual Basic .NET)

Copy Code
'represents a stock in an application Public Class Stock 'declare a delegate for the event Delegate Sub
AskPriceDelegate(ByVal aPrice As Object) 'declare the event using the delegate Public Event
AskPriceChanged As AskPriceDelegate 'instance variable for ask price Dim _askPrice As Object
'property for ask price Public WriteOnly Property AskPrice() Set(ByVal value As Object) _askPrice =
value RaiseEvent AskPriceChanged(_askPrice) End Set End Property End Class 'represents the user
interface in the application Public Class StockDisplay Public Sub Notify(ByVal anObject As Object)
Console.WriteLine("The new ask price is:" & anObject) End Sub End Class Public Class MainClass
Shared Sub Main() 'create new display and stock instances Dim stockDisplay As StockDisplay = New
StockDisplay() Dim stock As Stock = New Stock() Dim looper As Integer 'register the delegate
AddHandler stock.AskPriceChanged, AddressOf stockDisplay.Notify 'loop 100 times and modify the ask
price For looper = 0 To 100 _stock.AskPrice = looper Next looper 'unregister the delegate
RemoveHandler stock.AskPriceChanged, AddressOf stockDisplay.Notify End Sub
Once you are familiar with delegates and events, their inherent strengths become evident. Unlike the IObserver and
IObservable interfaces and ObservableImpl class, the use of delegates and events greatly simplifies the amount of work
that must be undertaken to implement this pattern. The CLR and complier provide the basis for observer container
management, as well as a common calling convention for registering, unregistering, and notifying observers. Perhaps the
greatest benefit of delegates is their intrinsic ability to refer to any method whatsoever (provided it conforms to the same
signature). This permits any class to act as an observer, independently of what interfaces it implements or classes it
specializes. Although the use of the IObserver and IObservable interfaces work to reduce the coupling between the
observer and subject classes, use of delegates completely eliminates it.

Event Pattern

Based on events and delegates, the FCL uses the Observer pattern quite extensively. The designers of the FCL fully realized
the inherent power of this pattern, applying it to both user interface and non-UI specific features throughout the Framework.
This use, however, is a slight variation on the base Observer pattern, which the Framework team has termed the Event
Pattern. In general, this pattern is expressed as formal naming conventions for delegates, events, and related methods
involved in the event notification process. Microsoft recommends that all applications and frameworks that utilize events and
delegates adopt this pattern, although there is no enforcement in the CLR or standard compiler (beware the pattern police!).

The first, and perhaps most important, of these conventions is the name of the event exposed by the subject. This name
should be self-evident as to the state change that it represents. Bear in mind that this convention, as with all other such
conventions, is subjective in nature. The intent is to provide clarity to those utilizing your event. The remaining items of the
event pattern leverage the proper naming of the event, thus the importance of this step to the pattern.
Returning to our trusty example, let us examine the impact of this convention on the Stock class. A suitable means of
deriving an event name is to utilize the name of the field that was modified in the subject class as the root. Since the name
of the field that is modified in the Stock class is the _askPrice, a reasonable event name would be AskPriceChanged. It is
fairly evident that the name of this event is far more descriptive than say, StateChangedInStockClass. Thus, the
AskPriceChanged event name adheres to the first convention.

The second convention in the Event pattern is properly naming of the delegate and its signature. The delegate name should
be composed of the event name (selected via the first convention) with the word Handler appended. The pattern calls for
the delegate to specify two parameters, the first supplying a reference to the sender of the event and the second providing
contextual information to the observer. The name of the first parameter is simply sender. This parameter must be typed as
System.Object. This is due to the fact the delegate could be bound to potentially any method on any class in the system.
The name of the second parameter, even simpler than the first, is e. This parameter is typed as System.EventArgs or some
derived class (more on this in a moment). Although the return type of the delegate depends on your implementation needs,
most delegates that implement this pattern do not return any value at all.

The second parameter of the delegate, e, requires slightly more attention. This parameter enables the subject object to pass
arbitrary contextual information to the observer. If such information is not required, an instance of System.EventArgs will
suffice, as instances of this class represent the absence of contextual data. Otherwise, a class derived from
System.EventArgs should be constructed with the appropriate implementation to provide this data. This class must be
named after the event name with the word EventArgs appended.

Referring to our Stock class, this convention requires that the delegate which handles the AskPriceChanged event to be
named, AskPriceChangedHandler. In addition, the name of the second parameter of this delegate should be named
AskPriceChangedEventArgs. Since we need to pass the new ask price to the observer, we need to extend the
System.EventArgs class, naming this class AskPriceChangedEventArgs, and providing the implementation to support
passing this data.

The last item in the Event pattern is the name and accessibility of the method on the subject class that is responsible for
firing the event. The name of this method should be composed of the event name with the addition of an On prefix. The
accessibility of this method should be set to protected. This convention applies only to non-sealed (NotInheritable in VB)
classes, as it serves as a well-known invocation point for derived classes to invoke observers registered with the base class.

Applying this last convention to the Stock class completes the Event pattern. Since the Stock class is not sealed, we must
add a method to fire the event. In accordance with the pattern, the name of this method is OnAskPriceChanged. The C#
and Visual Basic .NET code samples below show a complete view of the Event pattern applied to the Stock class. Note the
use of our specialization of the System.EventArgs class.

Event Pattern Example (C#)

Copy Code
public class Stock { //declare a delegate for the event public delegate void
AskPriceChangedHandler(object sender, AskPriceChangedEventArgs e); //declare the event using the
delegate public event AskPriceChangedHandler AskPriceChanged; //instance variable for ask price
object _askPrice; //property for ask price public object AskPrice { set { //set the instance variable
_askPrice=value; //fire the event OnAskPriceChanged(); } }//AskPrice property //method to fire event
delegate with proper name protected void OnAskPriceChanged() { AskPriceChanged(this,new
AskPriceChangedEventArgs(_askPrice)); }//AskPriceChanged }//Stock class //specialized event class for
the askpricechanged event public class AskPriceChangedEventArgs:EventArgs { //instance variable to
store the ask price private object _askPrice; //constructor that sets askprice public
AskPriceChangedEventArgs(object askPrice) { _askPrice=askPrice; } //public property for the ask price
public object AskPrice { get { return _askPrice; } } }//AskPriceChangedEventArgs

Event Pattern Example (Visual Basic .NET)

Public Class Stock

Conclusion

Based on this examination of the Observer pattern, it should be evident that this pattern provides an ideal mechanism to
ensure crisp boundaries between objects in an application, regardless of their function (UI or otherwise). Although fairly
simple to implement via callbacks (using the IObserver and IObservable interfaces), the CLR concepts of delegates and
events handle the majority of the "heavy lifting," as well as decreasing the level of coupling between subject and observer.
Proper use of this pattern really goes a long way to ensure that applications are able to evolve. As your UI and business
requirements change over time, the Observer pattern will ensure that your job is not as hard as it could be.

Used effectively, design patterns are a powerful tool in the development of flexible applications. This article was written to
demonstrate the soundness of the patterns approach, as well as to highlight one of the patterns used in the .NET Framework.
A future article will further explore the patterns in the FCL, as well as touch on some patterns for building effective Web
services.

Exploring the Factory Design Pattern

Introduction

Software changes. This is a rather obvious statement, but it is a fact that must be ever present in the minds of developers
and architects. Although we tend to think of software development as chiefly an engineering exercise, the analogy breaks
down very quickly. When was the last time someone asked the designers of the Empire State building to add ten new floors
at the bottom, put a pool on the top, and have all of this done before Monday morning?

This is a daunting challenge. We must design systems that are capable of changing at a moment's notice. Be it requirements,
technology, or personnel, there will be change and we must be prepared. If we forget this, we do so at our own peril.

Although this can be a frightening proposition, there are a great many tools at our disposal to ensure that systems are
designed to change rapidly while reducing the negative impact these alterations can bring. One such tool is design patterns.
Design patterns represent a wealth of collective knowledge and experience. The proper use of these patterns will help to
ensure that systems are malleable, enabling rapid change.

This article continues our discussion of these design patterns, which began with Exploring the Observer Design Pattern. This
series focuses on the examination of various design patterns and their use in the Microsoft® .NET Framework. Over the
course of this article, we will examine one of the most commonly used patterns, the Factory pattern.

Factory Pattern

An important facet of system design is the manner in which objects are created. Although far more time is often spent
considering the object model and instance interaction, if this simple design aspect is ignored it will adversely impact the
entire system. Thus, it is not only important what an object does or what it models, but also in what manner it was created.

Since most object-oriented languages and runtimes provide object instantiation (e.g. new, newobj, etc.) and initialization
(e.g. constructors) mechanisms, there may be a tendency to simply use these facilities directly without forethought to future
consequences. The overuse of this functionality often introduces a great deal of the inflexibility in the system, as the direct
use of a language/run-time object instantiation function creates an explicit association between the creator and created
classes. While associations are a necessary type of relationship in an object-oriented system, the coupling introduced
between classes is extremely difficult to overcome should requirements change (as they always do).

Since the need to reduce the inherent coupling associated with instance creation spans systems, it was not uncommon to see
the same types of solutions being used in a variety of different applications and frameworks. Formalized within Design
Patterns: Elements of Reusable Object-Oriented Software (Addison-Wesley Publishing Company, 1995), these solutions are
known as creational patterns. Creational patterns describe object-creation mechanisms that enable greater levels of reuse
in evolving systems.

One of the most widely used creational patterns is the Factory. This pattern is aptly named, as it calls for the use of a
specialized object solely to create other objects, much like a real-world factory. In the following sections, we will examine the
logical and physical models of this pattern, as well as discuss one such use of this pattern in the .NET Framework.

Logical Model

As with other design patterns, there are countless variations of the Factory pattern, although most variants typically used the
same set of primary actors, a client, a factory, and a product. The client is an object that requires an instance of another
object (the product) for some purpose. Rather than creating the product instance directly, the client delegates this
responsibility to the factory. Once invoked, the factory creates a new instance of the product, passing it back to the client.
Put simply, the client uses the factory to create an instance of the product. Figure 1 shows this logical relationship between
these elements of the pattern.

Figure 1. Factory pattern logical model

The factory completely abstracts the creation and initialization of the product from the client. This indirection enables the
client to focus on its discrete role in the application without concerning itself with the details of how the product is created.
Thus, as the product implementation changes over time, the client remains unchanged.

While this indirection is a tangible benefit, the most important aspect of this pattern is the fact that the client is abstracted
from both the type of product and the type of factory used to create the product. Presuming that the product interface is
invariant, this enables the factory to create any product type it deems appropriate. Furthermore, presuming that the factory
interface is invariant, the entire factory along with the associated products it creates can be replaced in a wholesale fashion.
Both of these radical modifications can occur without any changes to the client.

Consider an application that models the assembly of a variety of personal computers. The application contains a
ComputerAssembler class that is responsible for the assembly of the computer, a Computer class that models the
computer being built, and a ComputerFactory class that creates instances of the Computer class. In using the Factory
pattern, the ComputerAssembler class delegates responsibility for creation of Computer instances to the
ComputerFactory. This ensures that if the instantiation and/or initialization process changes (e.g. new constructor, use of
an activator, custom pooling, etc.), the ComputerAssembler does not need to change at all. This is the benefit of
abstracting the creation of an object from its use.

In addition, suppose that the business requirements changed and a new type of computer needs to be assembled. Rather
than modifying the ComputerAssembler class directly, the ComputerFactory class can be modified to create instances of
a new computer class (assuming that this new class has the same interface as Computer). Furthermore, it is also possible to
address this requirement by creating a new factory class (that has the same interface as ComputerFactory) that creates
instances of the new computer class (again, with the same interface as Computer). As before, nothing in the
ComputerAssembler class needs to change, all the logic just continues to work as it had previously. This is the benefit of
abstracting the types of the product and factory into invariant interfaces.

Physical Model

Most implementations of the Factory pattern use two abstract classes, Factory and Product, to provide the invariant
interfaces discussed in the logical model. Although we could utilize pure interfaces for this purpose, the use of abstract
classes enables us to place common instance behavior in the abstract class. In addition, abstract classes offer versioning
benefits over pure interfaces (see Base Class Usage Guidelines in the .NET Framework SDK for more information).

As shown in Figure 2, the Client uses an instance of a concrete subclass of Factory (ConcreteFactory) to create an
instance of a concrete Product subclass (ConcreteProduct). Since all variables, parameters, and method return values are
typed to the Factory and Product abstract classes, the Client is unaware of the introduction of these subclasses. This
enables the introduction of new Factory and Product subclasses as requirements warrant; nothing needs to change within
the Client. It is worth noting that this pattern does not dictate the use of the specific names (i.e. client, factory, product)
used within the physical model, rather the use of these names is only to provide clarity in terms of the role each type plays in
the pattern.

Figure 2. Factory pattern physical model

Using our previously defined computer assembly application, let's examine a simple implementation of the Factory pattern
coded in C# and in Visual Basic .NET.

Computer and Computer Factory Classes (C#)

Copy Code
abstract class Computer { public abstract int Mhz { get; } }//Computer abstract class
ComputerFactory { public abstract Computer GetComputer(); }//ComputerFactory

Computer and Computer Factory Classes (Visual Basic .NET)

Copy Code
MustInherit Class Computer Public MustOverride ReadOnly Property Mhz() As Integer End Class
MustInherit Class ComputerFactory Public MustOverride Function GetComputer() As Computer End
Class
The above code fragment outlines the Computer and ComputerFactory abstract classes. These types represent the
invariant factory and product interfaces required by the physical model. The ConcreteComputer and
ConcreteComputerFactory classes found below extend these abstract classes. The ConcreteComputer class overrides the
Mhz property of the Computer class, returning the value of 500. The ConceteComputerFactory overrides the
GetComputer method of the ComputerFactory class returning a new instance of ConcreteComputer.
Concrete Computer and Concrete Computer Factory (C#)

Copy Code
class ConcreteComputer:Computer { int _mhz = 500; public override int Mhz { get { return
_mhz; } }//Mhz }//ConcreteComputer class ConcreteComputerFactory:ComputerFactory { public
override Computer GetComputer() { return new
ConcreteComputer(); }//GetComputer }//ConcreteComputerFactory

Concrete Computer and Concrete Computer Factory (Visual Basic .NET)

Copy Code
Class ConcreteComputer Inherits Computer Private _mhz As Integer = 500 Public Overrides ReadOnly
Property Mhz() As Integer Get Return _mhz End Get End Property End Class Class
ConcreteComputerFactory Inherits ComputerFactory Public Overrides Function GetComputer() As
Computer Return New ConcreteComputer() End Function End Class
The ComputerAssembler class, found below, provides one method, AssembleComputer. This method accepts one
parameter that must be an object whose class extends the ComputerFactory abstract class. This method then uses this
factory instance to create an instance of some class that extends the Computer abstract class. Although the
ComputerAssembler is blissfully unaware of the actual subclass of Computer that it is using, it is still able to print its type
(via type introspection) and determine the MHz of the computer. The MainClass class, also found below, is the entry point
for the sample. It creates an instance of the ComputerAssembler and invokes the AssembleComputer method passing an
instance of a class that extends ComputerFactory.

ComputerAssembler and MainClass (C#)

Copy Code
class ComputerAssembler { public void AssembleComputer(ComputerFactory factory) { Computer
computer = factory.GetComputer(); Console.WriteLine("assembled a {0} running at {1} MHz",
computer.GetType().FullName, computer.Mhz); }//AssembleComputer }//ComputerAssembler class
MainClass { static void Main(string[] args) { ComputerFactory factory = new
ConcreteComputerFactory(); new
ComputerAssembler().AssembleComputer(factory); }//Main }//MainClass

ComputerAssembler and MainClass (Visual Basic .NET)

Copy Code
Class ComputerAssembler Public Sub AssembleComputer(ByVal factory As ComputerFactory) Dim
computer As Computer = factory.GetComputer() Console.WriteLine("assembled a {0} running at {1}
MHz", _ computer.GetType().FullName, computer.Mhz) End Sub End Class Class MainClass Public
Shared Sub Main() Dim args() As String = Environment.GetCommandLineArgs() Dim factory As
ComputerFactory = _ New ConcreteComputerFactory() Call (New
ComputerAssembler()).AssembleComputer(factory) End Sub End Class
In order to illustrate the benefits of factory and product type abstraction, suppose that the application was required to
assemble two different computer types, rather than only one. For the purposes of this example, we create an additional
factory, BrandXFactory, and a related product class, BrandXComputer, as shown below.
BrandXComputer and BrandXFactory (C#)

Copy Code
class BrandXComputer:Computer { int _mhz = 1500; public override int Mhz { get { return
_mhz; } }//Mhz }//BrandXComputer class BrandXFactory:ComputerFactory { public override Computer
GetComputer() { return new BrandXComputer(); }//GetComputer }//BrandXFactory

BrandXComputer and BrandXFactory (Visual Basic .NET)

Copy Code
Class BrandXComputer Inherits Computer Private _mhz As Integer = 1500 Public Overrides ReadOnly
Property Mhz() As Integer Get Return _mhz End Get End Property End Class Class BrandXFactory
Inherits ComputerFactory Public Overrides Function GetComputer() As Computer Return New
BrandXComputer() End Function End Class
With the new factory and product in place, we now need to modify the Main method of the MainClass to determine which
factory to use. If the appropriate string is passed in on the command line, the BrandXFactory will be used; if there is no
such command line argument, the standard ComputerFactory will be used. This modification is shown below.

MainClass (C#)

Copy Code
class MainClass { static void Main(string[] args) { ComputerFactory factory = null; if(args.Length > 0
&& args[0] == "BrandX") factory = new BrandXFactory(); else factory = new
ConcreteComputerFactory(); new
ComputerAssembler().AssembleComputer(factory); }//Main }//MainClass

MainClass (Visual Basic .NET)

Copy Code
Class MainClass Public Shared Sub Main() Dim args() As String = Environment.GetCommandLineArgs()
Dim factory As ComputerFactory = Nothing If args.Length > 0 And args(1) = "BrandX" Then factory =
New BrandXFactory() Else factory = New ConcreteComputerFactory() End If Call (New
ComputerAssembler()).AssembleComputer(factory) End Sub End Class
Please note that there is no modification or re-implementation of the ComputerAssembler class whatsoever. This class is
completely abstracted from the classes of the instances it assembles, as well as the creation and initialization of the same.

Factory Pattern in the .NET Framework

The Factory pattern has a long history at Microsoft. Those of you familiar with the internal workings of COM will no doubt
recall the use of the IClassFactory interface used to create instances of COM co-classes. While the programming landscape
has changed a great deal since the inception of COM, the benefits of this pattern were not lost on the designers of the .NET
Framework. As with many other design patterns, examples of the Factory pattern can be found throughout the Framework.
For the purposes of this article, we will examine one of the most notable uses of this pattern, which is found in Microsoft
ASP.NET.

A well-know feature of ASP.NET is the Web Forms code model, consisting of the Page framework and associated Web
Controls. Web Forms, in conjunction with other pieces of the .NET Framework, provide a rich development model for Web
applications. Less well known, although of equal import, is the HTTP Runtime. The classes within this runtime provide the
underlying HTTP request/response infrastructure required to support Web applications. Web Forms provide a high level of
abstraction over the HTTP Runtime, allowing developers to focus on domain-specific user interfaces and business logic.

When an ASP.NET page (*.aspx) is requested from a Web server, a variety of actions are performed. First and foremost, IIS
must determine what ISAPI extension will be used to service the request. Based on a set of pre-configured file extension
mappings stored in the metabase, IIS loads the appropriate ISAPI extension (aspnet_isapi.dll) and invokes the exported
HttpExtensionProc function. Assuming the ASP.NET process model is enabled (the default), the request is forward to the
ASP.NET worker process (aspnet_wp.exe). Acting as an unmanaged host for the common language runtime, this process
prepares the managed environment via numerous steps that culminate with the forwarding of the HTTP request to an
instance of the managed System.Web.Hosting.HttpRuntime class found in the System.Web.dll assembly.

Although this instance of HttpRuntime is ultimately responsible for processing the pending request, the logic required to do
so is not embedded within this class. If the designers of ASP.NET had made such a decision, every time the Web Forms code
and/or architecture changed, the HttpRuntime class would also need to be revisited as well. Rather, ASP.NET uses an
extensible mechanism to determine what logic to invoke when processing a request.

When the HttpRuntime::ProcessRequest method is invoked, a number of classes are utilized to determine which handler
should process the request. These handlers contain the actual logic required to process the request. Handlers are classes that
implement the System.Web.IHttpHandler interface. How does the HttpRuntime::ProcessRequest method determine
what handler to invoke? Not surprisingly, it relies on the Factory pattern.

If you have ever had the opportunity to examine the machine.config file, which provides the majority of the configuration
information for the .NET Framework, you may have noticed the <httphandler> section under the <system.web> element
(this file is located in the CONFIG subdirectory of the .NET Framework directory—on my machine
C:\WINNT\Microsoft.NET\Framework\v1.0.3705\CONFIG). This segment of this config file provides a mapping between HTTP
verbs, file extensions, and classes that implement the System.Web.IHttpHandlerFactory interface (classes that
implement IHttpHandler interface can also be registered here, but that is not germane to our discussion). The following
shows the default mapping for ASP.NET pages (*.aspx):

Copy Code
<httpHandlers> <add verb="*" path="*.aspx" type="System.Web.UI.PageHandlerFactory"/>
</httpHandlers>
When a request for an ASP.NET page is presented to the HttpRuntime instance, this mapping is consulted to determine
what class instance should be utilized as a factory to create the correct handler instance. As the
System.Web.UI.PageHandlerFactory class is registered to perform this role, a new instance is created and the
IHttpHandlerFactory::GetHandler method is invoked. This method returns an instance of the System.Web.UI.Page
class to which the HttpRuntime instance delegates the request by invoking the IHttpHandler::ProcessRequest method.
The following sequence diagram shown in Figure 3 highlights this process. Please note that a number of classes, in addition
to method parameters, have been omitted for the sake of brevity.
Figure 3. ASP.NET request processing

Creating your own specialized factory and associated handler is a fairly trivial exercise. The first step is the creation of
classes that implement the IHttpHandlerFactory and IHttpHandler interfaces, as shown below.

Custom HttpHandlerFactory and HttpHandler (C#)

Copy Code
public class HttpHandlerFactoryImpl:IHttpHandlerFactory { IHttpHandler
IHttpHandlerFactory.GetHandler( HttpContext context, String requestType, String url, String
pathTranslated ) { return new HttpHandlerImpl(); }//IHttpHandlerFactory.GetHandler void
IHttpHandlerFactory.ReleaseHandler( IHttpHandler handler) { /*no-op*/ } }//HttpHandlerFactoryImpl
public class HttpHandlerImpl:IHttpHandler { void IHttpHandler.ProcessRequest(HttpContext context) {
context.Response.Write("sample handler invoked..."); }//ProcessRequest bool IHttpHandler.IsReusable
{ get { return false; } } }//HttpHandlerImpl

Custom HttpHandlerFactory and HttpHandler (Visual Basic .NET)

Copy Code
Public Class HttpHandlerFactoryImpl Implements IHttpHandlerFactory Public Function
GetHandler(ByVal context As HttpContext, _ ByVal requestType As String, ByVal url As String, _ ByVal
pathTranslated As String) As IHttpHandler Implements _ IHttpHandlerFactory.GetHandler Return New
HttpHandlerImpl() End Function Public Sub ReleaseHandler(ByVal handler As IHttpHandler) _
Implements IHttpHandlerFactory.ReleaseHandler 'no-op End Sub End Class Public Class
HttpHandlerImpl Implements IHttpHandler Public Sub ProcessRequest(ByVal context As HttpContext) _
Implements IHttpHandler.ProcessRequest context.Response.Write("sample handler invoked...") End
Sub Public ReadOnly Property IsReusable() As Boolean _ Implements IHttpHandler.IsReusable Get
Return False End Get End Property End Class
The second step is the creation of the mapping between the HTTP verb, file extension, and factory class. Although this
mapping can be placed in the <httpHandlers> section of the machine.config file, the recommended approach is to simply
add this section to the web.config file located in the virtual directory of the Web application. When HTTP Runtime searches
for handlers it will look in both the machine.config and web.config files. The following configuration segment shows that
all HTTP request types (POST, GET, etc.) targeting files with the .sample extension will be handled by instances created by
the previously defined HttpHandlerFactoryImpl factory class.

Copy Code
<httpHandlers> <add verb="*" path="*.sample" type="HttpHandlerFactoryImpl,SampleHandler" />
</httpHandlers>
The final step is the registration of the .sample file extension with IIS. In order for the ASP.NET HTTP Runtime to be invoked
when a given file is requested, the file's extension must be mapped to the ASP.NET ISAPI extension (asp_isapi.dll). This
task can be accomplished via the MMC snap-in for IIS by adding a new application extension mapping in the Web application
configuration (as shown in Figure 4).

Figure 4. Registering the .sample extension

Conclusion

As we conclude this examination of the of the Factory pattern, it should be apparent that this pattern offers considerable
benefits. From the abstraction of instance creation to the use of immutable product and factory interfaces, this pattern
provides a clear mechanism to design flexible system that are highly adaptable. The inclusion of this pattern in the .NET
Framework is a clear testament to it usefulness. Regardless of the nature of your application, this pattern can help it weather
the winds of change.

Potrebbero piacerti anche