Skip to content

Commit 665dd40

Browse files
committed
Abstract Factory implemented
1 parent f69aa4e commit 665dd40

File tree

10 files changed

+425
-5
lines changed

10 files changed

+425
-5
lines changed
Lines changed: 33 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,33 @@
1+
using System;
2+
using System.Collections.Generic;
3+
using System.Linq;
4+
using System.Text;
5+
using System.Threading.Tasks;
6+
7+
namespace CreationalPatterns.AbstractFactory
8+
{
9+
public interface Dough
10+
{
11+
string GetName();
12+
}
13+
14+
public class ThickCrustDough : Dough
15+
{
16+
private string name = "Extra thick crust dough";
17+
18+
public string GetName()
19+
{
20+
return name;
21+
}
22+
}
23+
24+
public class ThinCrustDough : Dough
25+
{
26+
private string name = "Thin crust dough";
27+
28+
public string GetName()
29+
{
30+
return name;
31+
}
32+
}
33+
}
Lines changed: 76 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,76 @@
1+
using System;
2+
using System.Collections.Generic;
3+
using System.Linq;
4+
using System.Text;
5+
using System.Threading.Tasks;
6+
7+
namespace CreationalPatterns.AbstractFactory
8+
{
9+
public enum PizzaType
10+
{
11+
Cheese,
12+
Veggie
13+
};
14+
15+
public abstract class Pizza
16+
{
17+
public string Name { get; set; }
18+
public Dough Dough { get; set; }
19+
20+
public abstract void Prepare();
21+
22+
public void Bake()
23+
{
24+
Console.WriteLine("Bake for 15 minutes");
25+
}
26+
27+
public void cut()
28+
{
29+
Console.WriteLine("Cutting the pizza into 8 slices");
30+
}
31+
32+
public void box()
33+
{
34+
Console.WriteLine("Pack the pizza in a box");
35+
}
36+
}
37+
38+
// American Pizzas
39+
public class CheesePizza : Pizza{
40+
private string description = "Cheese Pizza";
41+
private PizzaIngredientFactory ingredientFactory;
42+
43+
public CheesePizza(PizzaIngredientFactory ingredientFactory)
44+
{
45+
this.ingredientFactory = ingredientFactory;
46+
this.Name = ingredientFactory.GetName() + " Style " + description;
47+
}
48+
49+
public override void Prepare()
50+
{
51+
Console.WriteLine("Preparing {0}", this.Name);
52+
this.Dough = ingredientFactory.CreateDough();
53+
Console.WriteLine("Creating {0}", this.Dough.GetName());
54+
}
55+
}
56+
57+
public class VeggiePizza : Pizza
58+
{
59+
private string description = "Veggie Pizza";
60+
private PizzaIngredientFactory ingredientFactory;
61+
62+
public VeggiePizza(PizzaIngredientFactory ingredientFactory)
63+
{
64+
this.ingredientFactory = ingredientFactory;
65+
this.Name = ingredientFactory.GetName() + " Style " + description;
66+
}
67+
68+
public override void Prepare()
69+
{
70+
Console.WriteLine("Preparing {0}", this.Name);
71+
this.Dough = ingredientFactory.CreateDough();
72+
Console.WriteLine("Creating {0}", this.Dough.GetName());
73+
}
74+
}
75+
76+
}
Lines changed: 40 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,40 @@
1+
using System;
2+
using System.Collections.Generic;
3+
using System.Linq;
4+
using System.Text;
5+
using System.Threading.Tasks;
6+
7+
namespace CreationalPatterns.AbstractFactory
8+
{
9+
public interface PizzaIngredientFactory
10+
{
11+
string GetName();
12+
Dough CreateDough();
13+
}
14+
15+
public class AmericanPizzaIngredientFactory : PizzaIngredientFactory
16+
{
17+
public Dough CreateDough()
18+
{
19+
return new ThickCrustDough();
20+
}
21+
22+
public string GetName()
23+
{
24+
return "American";
25+
}
26+
}
27+
28+
public class ItalianPizzaIngredientFactory : PizzaIngredientFactory
29+
{
30+
public Dough CreateDough()
31+
{
32+
return new ThinCrustDough();
33+
}
34+
35+
public string GetName()
36+
{
37+
return "Italian";
38+
}
39+
}
40+
}
Lines changed: 68 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,68 @@
1+
using System;
2+
using System.Collections.Generic;
3+
using System.Linq;
4+
using System.Text;
5+
using System.Threading.Tasks;
6+
7+
namespace CreationalPatterns.AbstractFactory
8+
{
9+
10+
public abstract class PizzaStore
11+
{
12+
public Pizza OrderPizza(PizzaType type)
13+
{
14+
// calls the factory method to create pizza
15+
Pizza pizza = CreatePizza(type);
16+
17+
pizza.Prepare();
18+
pizza.Bake();
19+
pizza.cut();
20+
pizza.box();
21+
22+
return pizza;
23+
}
24+
25+
// A facotry method
26+
// 1. is abstract so the subclass are counted on to handle object creation.
27+
// 2. returns a Product.
28+
// 3. isolates the client from knowing what of concrete Product is actually created.
29+
// 4. may be parameterized (or not) to select among several variations of a product.
30+
protected abstract Pizza CreatePizza(PizzaType type);
31+
}
32+
33+
public class AmericanPizzaStore : PizzaStore
34+
{
35+
private PizzaIngredientFactory ingredientFactory = new AmericanPizzaIngredientFactory();
36+
37+
protected override Pizza CreatePizza(PizzaType type)
38+
{
39+
switch (type)
40+
{
41+
case PizzaType.Cheese:
42+
return new CheesePizza(ingredientFactory);
43+
case PizzaType.Veggie:
44+
return new VeggiePizza(ingredientFactory);
45+
default:
46+
throw new NotImplementedException();
47+
}
48+
}
49+
}
50+
51+
public class ItalianPizzaStore : PizzaStore
52+
{
53+
private PizzaIngredientFactory ingredientFactory = new ItalianPizzaIngredientFactory();
54+
55+
protected override Pizza CreatePizza(PizzaType type)
56+
{
57+
switch (type)
58+
{
59+
case PizzaType.Cheese:
60+
return new CheesePizza(ingredientFactory);
61+
case PizzaType.Veggie:
62+
return new VeggiePizza(ingredientFactory);
63+
default:
64+
throw new NotImplementedException();
65+
}
66+
}
67+
}
68+
}
Lines changed: 47 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,47 @@
1+
# Factory Method
2+
3+
The Factory Method Pattern defines an interface for creating an object, but lets subclasses decide which class to instantiate.
4+
5+
A factory method
6+
* handles object creation and
7+
* encapsulates it in a subclass.
8+
9+
**Definition**
10+
```cs
11+
// A facotry method
12+
// 1. is abstract so the subclass are counted on to handle object creation.
13+
// 2. returns a Product.
14+
// 3. isolates the client from knowing what of concrete Product is actually created.
15+
// 4. may be parameterized (or not) to select among several variations of a product.
16+
protected abstract Pizza CreatePizza(PizzaType type);
17+
```
18+
19+
![Pizza Store with Factory Method](/Diagrams/FactoryMethod.png)
20+
21+
**Usage**
22+
```cs
23+
PizzaStore americanStore = new AmericanPizzaStore();
24+
Pizza pizza = americanStore.OrderPizza(PizzaType.Veggie);
25+
Console.WriteLine("Esposito ordered a " + pizza.Name);
26+
27+
// Italian Pizza Store
28+
PizzaStore italianStore = new ItalianPizzaStore();
29+
Pizza pizza = italianStore.OrderPizza(PizzaType.Cheese);
30+
Console.WriteLine("Esposito ordered a " + pizza.Name);
31+
```
32+
33+
## Common Structure
34+
35+
![Common structure of factory method pattern](http://www.dofactory.com/images/diagrams/net/factory.gif)
36+
37+
* Product (Pizza)
38+
* defines the interface of objects the factory method creates
39+
* ConcreteProduct (ItalianCheesePizza, AmericanCheesePizza etc.)
40+
* implements the Product interface
41+
* Creator (PizzaStore)
42+
* declares the abstract factory method which returns an instance of type Product.
43+
* may call the factory method to return an instance (OrderPizza calls CreatePizza)
44+
* ConcreteCreator(AmericanPizzaStore)
45+
* overrides the abstract factory method to return an instance of a ConcreteProduct (eg. AmericanCheesePizza)
46+
47+
_[Source: http://www.dofactory.com/net/factory-method-design-pattern]_
Lines changed: 19 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,19 @@
1+
using System;
2+
using System.Collections.Generic;
3+
using System.Linq;
4+
using System.Text;
5+
using System.Threading.Tasks;
6+
7+
namespace CreationalPatterns.AbstractFactory
8+
{
9+
public class TestAbstractFactory
10+
{
11+
public static void run()
12+
{
13+
PizzaStore americanStore = new AmericanPizzaStore();
14+
Pizza pizza = americanStore.OrderPizza(PizzaType.Veggie);
15+
Console.WriteLine("Esposito ordered a " + pizza.Name);
16+
Console.ReadLine();
17+
}
18+
}
19+
}

CreationalPatterns/CreationalPatterns.csproj

Lines changed: 8 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -43,6 +43,11 @@
4343
<Reference Include="System.Xml" />
4444
</ItemGroup>
4545
<ItemGroup>
46+
<Compile Include="AbstractFactory\Dough.cs" />
47+
<Compile Include="AbstractFactory\Pizza.cs" />
48+
<Compile Include="AbstractFactory\PizzaIngredientFactory.cs" />
49+
<Compile Include="AbstractFactory\PizzaStore.cs" />
50+
<Compile Include="AbstractFactory\TestAbstractFactory.cs" />
4651
<Compile Include="FactoryMethod\Pizza.cs" />
4752
<Compile Include="FactoryMethod\PizzaStore.cs" />
4853
<Compile Include="FactoryMethod\TestPizzaFactoryMethod.cs" />
@@ -52,14 +57,14 @@
5257
<Compile Include="Singleton\ChocolateBoiler_ThreadSafe.cs" />
5358
</ItemGroup>
5459
<ItemGroup>
60+
<None Include="AbstractFactory\README.md" />
5561
<None Include="App.config" />
62+
<None Include="doc\AbstractFactory.cd" />
5663
<None Include="doc\FactoryMethod.cd" />
5764
<None Include="doc\Singleton.cd" />
5865
<None Include="FactoryMethod\README.md" />
5966
</ItemGroup>
60-
<ItemGroup>
61-
<Folder Include="AbstractFactory\" />
62-
</ItemGroup>
67+
<ItemGroup />
6368
<Import Project="$(MSBuildToolsPath)\Microsoft.CSharp.targets" />
6469
<!-- To modify your build process, add your task inside one of the targets below and uncomment it.
6570
Other similar extension points exist, see Microsoft.Common.targets.

CreationalPatterns/Program.cs

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -1,4 +1,4 @@
1-
using CreationalPatterns.FactoryMethod;
1+
using CreationalPatterns;
22
using System;
33
using System.Collections.Generic;
44
using System.Linq;
@@ -11,7 +11,7 @@ class Program
1111
{
1212
static void Main(string[] args)
1313
{
14-
TestPizzaFactoryMethod.run();
14+
AbstractFactory.TestAbstractFactory.run();
1515
}
1616
}
1717
}

0 commit comments

Comments
 (0)