Abstract Factory is one of the 23 Design Patterns elucidated in the most excellent book Design Patterns: Elements of Reusable Object - Oriented Software by Gamma and Helm et al. ISBN 0201633612 , which is cited below:
For a cool VFP factory idiom, see VFPSession Factory.
Intent: Provide an interface for creating families of related or dependent objects without specifying their concrete classes.
Design Pattern Classification: Creational Object
Applicability: Use the Abstract Factory pattern when
a system should be independent of how its products are created, composed, and represented.
a system should be configured with one of multiple families of products.
a family of related product objects is designed to be used together, and you need to enforce this constraint.
you want to provide a class library of products, and you want to reveal just their interfaces, not their implementations.
Abstract Factory (WidgetFactory): declares an interface for operations that create abstract product objects.
AbstractProduct (Window, ScrollBar): declares an interface for a type of product object.
ConcreteProduct (MotifWindow, MotifScrollBar) defines a product object to be created by the corresponding concrete factory. Implements the AbstractProduct interface.
Client: uses only interfaces declared by Abstract Factory and AbstractProduct classes.
Normally a single instance of a ConcreteFactory class is created at run-time. This concrete factory creates product objects having a particular implementation. To create different product objects, clients should use a different concrete factory.
Abstract Factory defers creation of product objects to its ConcreteFactory subclass.
The Abstract Factory pattern has the following benefits and liabilities:
It isolates concrete classes. The Abstract Factory pattern helps you control the classes of objects that an application creates. Because a factory encapsulates the responsibility and the process of creating product objects, it isolates clients from implementation classes. Clients manipulate instances through their abstract interfaces. Product class names are isolated in the implementation of the concrete factory; they do not appear in client code.
It makes exchanging product families easy. The class of a concrete factory appears only once in an application?that is, where it's instantiated. This makes it easy to change the concrete factory an application uses. It can use different product configurations simply by changing the concrete factory. Because an abstract factory creates a complete family of products, the whole product family changes at once. In our user interface example, we can switch from Motif widgets to Presentation Manager widgets simply by switching the corresponding factory objects and recreating the interface.
It promotes consistency among products. When product objects in a family are designed to work together, it's important that an application use objects from only one family at a time. Abstract Factory makes this easy to enforce.
Supporting new kinds of products is difficult. Extending abstract factories to produce new kinds of Products isn't easy. That's because the Abstract Factory interface fixes the set of products that can be created. Supporting new kinds of products requires extending the factory interface, which involves changing the Abstract Factory class and all of its subclasses. We discuss one solution to this problem in the Implementation section. In VFP it's relatively easy to data drive the factory, which makes it extremely easy to add new Products to the factory.
Specific to VFP, if the factory actually issues Create Object() the object will be instantiated in whatever data session the factory was created in. It's often desirable to simply have the factory return the name of the class to be instantiated, then let the caller actually create the object, using something like Create Object(oFactory.GetClass("My Class")). -- Mike Feltman
Even more specific to VFP, the factory can be table driven, so the actual names of the classes to use can be further separated, behind their logical names. The "make me a TwoHolesButton" becomes Create Object(oFactory.GetClass("TwoHolesButton") which finds it under a PK of 3210, which in yet another table finds the TwoSquareHolesOctangularButton as the actual class. Since both levels of names are in tables, and the class is instantiated from a standalone .vcx, updates or reconfiguration of such an app is easy and feasible at runtime. Downside: deliver vcxes and these tables as separate files, and maintain them. I saw (helped) this to work, and it worked great. -- Dragan Nedeljkovich
As you say, there are a number of extra steps involved to instantiate the "TwoHolesButton". As always, this flexibility is coming at the price of performance. It becomes important to know when to apply this design pattern. -- Mike Yearwood
I'm trying to get a better handle on the factory pattern. Would a potential class definition for this be:
Function ReturnDialogForm() as DialogForm
Function ReturnDataEntryForm as DataEntryForm
Function ReturnForm(cFormType) as ????
It seems that a strongly typed language would have an issue with the second definition. But the first one is less flexible. Any comments would be appreciated.
A strongly typed language would have no problem with the second class definition since you'd define it as
Function ReturnForm(cFormType) as SomeBaseForm
SomeBaseForm is a superclass of the forms you'd be building. -- Steven Black
See Also: VFP Design Pattern Catalog Abstract Factory Use Cases
Category Design Patterns
( Topic last updated: 2004.04.23 06:53:12 PM )