In this article we will look into how to use the structure map in the Factory Pattern.
Introduction
StructureMap is a "Inversion of Control Container" that makes managing the complexity of designing software using the "Dependency Inversion Principle" (DIP) easier.
In this article we will look into how to use the structure map in the Factory Pattern.
First of all we will create an example of Factory Pattern without using Structure Map and then we will use Structure Map in the same example to demonstrate it's concept and power.
Factory pattern without using Structure Map
using System;
namespace FactoryPattern
{
public class ExampleWithoutStructureMap
{
Factory f = new Factory();
public void CallMe()
{
f.GetObject("dog");
}
}
public interface ISpeak
{
void Speak();
}
class Cat : ISpeak
{
public void Speak()
{
Console.WriteLine("Cat says Meo");
}
}
class Dog : ISpeak
{
public void Speak()
{
Console.WriteLine("Dog barks");
}
}
class Factory
{
// Decides which class to instantiate.
public ISpeak GetObject(string name)
{
ISpeak instance = null;
switch (name)
{
case "dog":
instance = new Dog();
instance.Speak();
break;
case "cat":
instance = new Cat();
instance.Speak();
break;
}
return instance;
}
}
}
The concreate classes are all getting derived from the "ISpeak" interface.And in the FactoryMethod we are creating the instances of the concrete factories.
We can make out that the factory method has the concrete class instances created inside it.Can we invert it ? For that reason we will use IOC container i.e. StructureMap here.
First of all let us get the StructureMap.dll from it's home page and add it to our assembly.
Next let us write the below code
using System;
using StructureMap;
namespace FacrtoryPatternWithStructureMap
{
public class ExampleWithStructureMap
{
Factory f = new Factory();
public void CallMe()
{
f.FactoryMethod("dog");
}
}
public interface ISpeak
{
void Speak();
}
class Cat : ISpeak
{
public void Speak()
{
Console.WriteLine("Cat says Meo");
}
}
class Dog : ISpeak
{
public void Speak()
{
Console.WriteLine("Dog barks");
}
}
class Factory
{
/// <summary>
/// Decides which class to instantiate.
/// </summary>
public ISpeak FactoryMethod(string name)
{
InitializeObject();
ISpeak instance = ObjectFactory.GetNamedInstance<ISpeak>(name);
instance.Speak();
return instance;
}
private static void InitializeObject()
{
ObjectFactory.Initialize(x =>
{
x.For<ISpeak>().Use<Dog>().Named("dog");
x.For<ISpeak>().Use<Cat>().Named("cat");
});
}
}
}
We initialize the Container or ObjectFactory using the "Initialize" method.This method follows the "nested closure" pattern where we have to provide it with an Action<T> lambda function to configure ObjectFactory.
The expression "x.For<ISpeak>().Use<Dog>().Named("dog")" means that,when we ask for a "ISpeak", it should return "Dog" since we are setting the name of the instance via the "Named" method.
The ObjectFactory.GetNamedInstance<ISpeak>(name), creates or finds the named instance of ISpeak.
References
- http://dotnet.dzone.com/articles/di-structuremap-quickstart
- StructureMap
- Introduction to StructureMap
Conclusion
Hope this will be helpful.Thanks for reading.Zipped file is attached.