Su Creator
clase es la fábrica. Vamos a llamarlo ProductFactory
, para hacer el ejemplo más explícito.
(estoy asumiendo que usted está utilizando C++)
class Book : public Product
{
};
class Computer : public Product
{
};
class ProductFactory
{
public:
virtual Product* Make(int type)
{
switch (type)
{
case 0:
return new Book();
case 1:
return new Computer();
[...]
}
}
}
llamada así:
ProductFactory factory = ....;
Product* p1 = factory.Make(0); // p1 is a Book*
Product* p2 = factory.Make(1); // p2 is a Computer*
// remember to delete p1 and p2
lo tanto, para responder a su pregunta:
Lo que lo hace tiene que ver con las subclases? ¿Y para qué se supone que debo usar las subclases ?
cuál es la definición de patrón de la fábrica está diciendo es que la fábrica define una API común para la creación de instancias de un tipo determinado (normalmente una interfaz o clase abstracta), pero el tipo real de las implementaciones volvió (por lo tanto la subclase referencia) es responsabilidad de la fábrica. En el ejemplo, la fábrica devuelve instancias Product
, para las cuales Book
y Computer
son subclases válidas.
Existen otras expresiones idiomáticas para la fábrica, como tener una API para la fábrica y las implementaciones concretas de la fábrica no aceptar una type
como en mi ejemplo, pero que están acoplados con el tipo de instancias volvió, como este :
class ProductFactory
{
public:
virtual Product* Make() = 0;
}
class BookProductFactory : public ProductFactory
{
public:
virtual Product* Make()
{
return new Book();
}
}
En esta clase BookProductFactory
siempre devuelve Book
casos.
ProductFactory* factory = new BookProductFactory();
Product* p1 = factory->Make(); // p1 is a Book
delete p1;
delete factory;
Para que quede claro, ya que parece que hay un poco de confusión entre Abstract Factory
y Factory method
patrones de diseño, vamos a ver un ejemplo concreto:
Usando Abstract Factory
class ProductFactory {
protected:
virtual Product* MakeBook() = 0;
virtual Product* MakeComputer() = 0;
}
class Store {
public:
Gift* MakeGift(ProductFactory* factory) {
Product* p1 = factory->MakeBook();
Product* p2 = factory->MakeComputer();
return new Gift(p1, p2);
}
}
class StoreProductFactory : public ProductFactory {
protected:
virtual Product* MakeBook() { return new Book(); }
virtual Product* MakeComputer() { return new Computer(); }
}
class FreeBooksStoreProductFactory : public StoreProductFactory {
protected:
virtual Product* MakeBook() {
Book* b = new FreeBook(); // a FreeBook is a Book with price 0
return b;
}
}
Eso se usa así:
Store store;
ProductFactory* factory = new FreeBooksStoreProductFactory();
Gift* gift = factory->MakeGift(factory);
// gift has a FreeBook (Book with price 0) and a Computer
delete gift;
delete factory;
Utilizando el método de fábrica
class Store {
public:
Gift* MakeGift() {
Product* p1 = MakeBook();
Product* p2 = MakeComputer();
return new Gift(p1, p2);
}
protected:
virtual Product* MakeBook() {
return new Book();
}
virtual Product* MakeComputer() {
return new Computer();
}
}
class FreeBooksStore : public Store {
protected:
virtual Product* MakeBook() {
Book* b = new FreeBook(); // a FreeBook is a Book with price 0
return b;
}
}
que se utiliza como esto:
Store* store = new FreeBooksStore();
Gift* gift = store->MakeGift();
// gift has a FreeBook (Book with price 0) and a Computer
delete gift;
delete store;
Cuando se utiliza un discriminador type
como lo hice en el ejemplo original, estamos utilizando parametized factory methods
- un método que sabe cómo crear diferentes tipos de objetos. Pero eso puede aparecer en un patrón Abstract Factory
o Factory Method
. Un pequeño truco: si está ampliando la clase de fábrica, está utilizando Abstract Factory. Si amplía la clase con los métodos de creación, entonces está utilizando métodos de fábrica.
entonces, en su código, ProductFactory es una fábrica abstracta, y make es el método de fábrica, ¿no? – Alcott
La diferencia entre 'Abstract Factory' y' Factory Method' sería una pregunta por sí misma. En resumen, cuando usa un discriminador de tipo como lo hice en el ejemplo, estamos usando "métodos de fábrica parametrizados", un método que sabe cómo crear diferentes tipos de objetos. Pero eso puede aparecer en un patrón Abstract Factory o Factory Method. Un pequeño truco: si está ampliando la clase de fábrica, está utilizando 'Abstract Factory'. Si amplía la clase con _factory methods_, entonces está utilizando 'Factory Methods'. Si la diferencia aún no está clara, plantee una pregunta diferente sobre SO. –
Para dejarlo en claro. Mi respuesta no utiliza el patrón de diseño 'Método de fábrica' sino el patrón de diseño' Fábrica abstracta'. –