Download presentation
Presentation is loading. Please wait.
1
Summary prepared by Kirk Scott
Unit 22 Abstract Factory Summary prepared by Kirk Scott
2
Design Patterns in Java Chapter 17 Abstract Factory
Summary prepared by Kirk Scott
3
The Introduction Before the Introduction
Like some of the other patterns in this group, this pattern turns out to be pretty simple The book, as usual, tries to provide several examples with context Although more information should be useful, the presentation seems to partially confuse the presentation of the basic pattern I will try to work through this, adding explanations that help keep it clear what part of the material directly illustrates the pattern and what is background
4
Book definition: The intent of the Abstract Factory, or Kit, is to allow creation of families of related or dependent objects.
5
Comment mode on, 1: The name of the pattern includes the word abstract For better or worse, the book’s examples don’t include an abstract class Instead, the examples show a concrete superclass and a subclass of it It seems that an example that more closely followed the name of the pattern would have an abstract class and two concrete subclasses of it
6
Comment mode on, 2: Once you see the word kit in the book definition, you might be put in mind of the chapter on facades There, the goal was to create a class that made it easy to use a toolkit or utility, for example In a way, that chapter worked at its goal backwards The examples identified application specific logic and implemented that in a set of classes
7
The façade was a class that made it easier to create and use graphical user interface elements in the application Even though the point of those examples was the façade, the heavy work was in dealing with the application specific parametric equations It was almost as if the leftovers in the design ended up in the UI class, which was the facade
8
In this chapter, the emphasis is on the user interface stuff
In fact, you might regard the user interface class as a façade into the Java API However, at this time the façade aspects of the design are not what the book is emphasizing In effect, what’s happening is that the façade idea is being expanded out into a set of classes It’s this expansion into a set of classes that’s of interest
9
In its simplest form, this is how the book illustrates what’s going on
In a base UI class you define methods that will return instances of graphical user interface components that have certain features For example, an application may require a button
10
Rather than having the application construct an instance of JButton directly, it acquires a JButton object by calling a UI method The method that constructs the JButton takes care of the details of what kind of construction parameters it will use
11
This grows into the Abstract Factory design pattern in this way:
What if you would like it to be possible for the application to seamlessly use JButtons of a different form? The you extend the UI class, overriding those methods where you would like the visual aspects to change
12
The application can use the subclass of the original UI class
When the application calls the method to get an instance of a JButton, it will get the kind defined in the subclass
13
A Classic Example: GUI Kits
A GUI kit is an implementation of the Abstract Factory design pattern The GUI kit supplies components to client applications These components are things like buttons or other graphical user interface components The kit constructs the component objects, passing in parameters so that together they have a consistent look and feel
14
A simple illustration of the abstract factory idea is given in the UML diagram on the next overhead
The UI class implements methods that have to do with the visual appearance of an application Notice that the diagram includes a BetaUI subclass This represents the idea that if desired, the same set of methods could be provided, but returning objects with different visual characteristics
16
Before going any further, observe the following:
It might be a better illustration of the pattern overall if there were an abstract superclass AbstractUI Then this could have two subclasses, NormalUI and BetaUI However, the book has chosen to do it with a simple superclass and subclass, so the example will be pursued in that way
17
The UML diagram on the following overhead illustrates the idea that a client application makes use of the UI class Specifically, it previews the idea that the undoButton of the application may be derived from the createButton() method, or some similar method in the UI class If, in the diagram, the BetaUI class were substituted for the UI class, then the Visualization application would get a different look and feel
19
The application makes it possible to:
The book illustrates the idea with what is in reality a pretty simple example The figure on the next overhead illustrates the graphical user interface for a Visualization application The application makes it possible to: add icons representing machines, click and drag them around the work area, and undo a recent action, like adding a machine
21
The figure on the next overhead shows the application with (slight) changes in the user interface
The add and undo button images have been changed from rockets to cherries The text under the images has been made italic Yes, the change could be made by simply hardcoding a change somewhere in the UI However, it will be accomplished by creating a subclass of UI which has these different characteristics hardcoded into it
23
The UML diagram for the UI class showed these methods:
createButton(), getFont(), createPaddedPanel(), and getIcon()
24
This is only a subset of the methods it would contain
In continuing the example, the book considers these methods: createButton(), createButtonOk(), and createButtonCancel() Code for these is given on the following overheads
25
public JButton createButton()
{ JButton button = new JButton(); button.setSize(128, 128); button.setFont(getFont()); button.setVerticalTextPosition(AbstractButton.BOTTOM); button.setHorizontalTextPosition(AbstractButton.CENTER); return button; }
26
public JButton createButtonOk()
{ JButton button = createButton(); button.setIcon(getIcon(“images/rocket-large.gif”)); button.setText(“Ok!”); return button; }
27
public JButton createButtonCancel()
{ JButton button = createButton(); button.setIcon(getIcon(“images/rocket-large-down.gif”)); button.setText(“Cancel!”); return button; }
28
Notice that the creation of the OK and the Cancel buttons make use of the creation of a simple button In this code, the use of the rocket icon/image is hardcoded into the characteristics of the buttons Then in the visualization application, these button creation methods are used to create visual components
29
In particular, if you look at the constructor for the Visualization client, it takes an instance of the UI class as a parameter Also, the visualization has a (protected) instance variable named undoButton of the (super) type JButton
30
On the following overhead the code is given for a method named undoButton() in the visualization
This method returns an instance of an undoButton which it creates This method makes use of the button creation methods in the UI class
31
protected JButton undoButton()
{ if(undoButton == null) undoButton = ui.createButtonCancel(); undoButton.setText(“Undo”); undoButton.setEnabled(false); undoButton.addActionListener(mediator.undAction()); } return undoButton;
32
The visualization code accepts a UI object as a construction parameter
This means that the look and feel of the visualization can be changed by passing it an instance of an equivalent, but different UI
33
This requires no change in the code of the visualization
This can be accomplished by making the new UI a subclass of the old one You can always pass in a subclass object when the parameter is typed to a superclass
34
The book continues the example by naming the subclass of UI BetaUI
The requirements for BetaUI are these: The image should a cherry instead of a rocket The font should be italic On the next overhead, partial code for BetaUI is given
35
public class BetaUI extends UI
{ public BetaUI() Font oldFont = getFont(); font = new Font( oldFont.getName(), oldFont.getStyle() | Font.ITALIC, oldFont.getSize()); } /* Notice that the plan is to make use of the superclass as much as possible. However, something somewhat devious may be going on here. The font instance variable is inherited. Its characteristics are being changed in the subclass. Is an instance variable being overridden? */
36
public JButton createButtonOk()
{ // Challenge! } public JButton createButtonCancel()
37
Challenge 17.1 Complete the code for the BetaUI class.
38
Solution 17.1 One solution is as follows: [See the following overheads.]
39
public JButton createButtonOk()
{ JButton b = super.createButtonOk(); b.setIcon(getIcon(“images/cherry-large.gif”)); return b; } public JButton creatButtonCancel() Jbutton b = super.createButtonCancel(); b.setIcon(getIcon(“images/cherry-large-down.gif”)); This code takes the approach of using the base class methods as much as possible.
40
The book illustrates how this works by giving the following code which uses the BetaUI class instead of the UI class public class ShowBetaVisualization { public static void main(String[] args) Jpanel panel = new Visualization(new BetaUI)); SwingFacade.launch(panel, “Operational Model”); }
41
The book states that this example illustrates the usefulness of the design pattern
However, it also states that the example has some shortcomings The shortcomings will be listed below After that the book will suggest an alternative design
42
One of the stated shortcomings is that, as written, the BetaUI class depends on the ability to override the creation methods It certainly seems up to this point that this was done intentionally Based on this observation alone, it’s not clear how this is a shortcoming It remains to be seen whether or how an alternative would avoid this
43
Another shortcoming, as stated by the book
The subclass methods need access to protected instance variables, like font, from the superclass First of all, I’m not a fan of the protected modifier Whether you use it or not, you still should have access with get and set methods It will not be clear exactly what the book means until its alternative is presented For the time being it’s not clear whether it’s hinting at the “overriding an instance variable” problem,
44
Challenge 17.2 Suggest a design change that would still allow for the development of a variety of GUI control factories but that would reduce the reliance of subclasses on method modifiers in the UI class. Comment mode on: As usual, there’s no reason to try and predict what the book will do until you see it. However, once you do see it, it will be clear that it was a simple application of something you know.
45
Solution 17.2 One solution for producing a more resilient design would be to specify the expected creation methods and standard GUI properties in an interface, as Figure B.20 shows. [See the next overhead.]
47
Comment mode on: I’m not convinced If BetaUI implemented the interface instead of extending UI, I can see how their goals might be accomplished As it is, structuring the application in this way might be a design convenience, but it’s not so clear that it solves the identified problems
48
Since interface methods are public by default, you’ve forced public methods, but you could have done that in the UI class anyway As for the instance variables, if each class implemented the interface, each would have to provide the needed variables As shown, BetaUI would still inherit instance variables from UI and “override” them
49
It may be that I just misunderstand what the book is trying to say
On the other hand, maybe there is a mistake in the diagram provided in the book
50
Maybe both UI and BetaUI were supposed to separately implement the GuiFactory interface
If so, such a design would approach the alternative that I mentioned at the beginning It would not be very different from having an abstract GuiFactory class with both UI and BetaUI as concrete subclasses
51
Comment mode off; back to topics in the book
The book observes that in a sense an abstract factory class is like a collection of factory methods Recall that a factory method was not just a method It was an arrangement of classes and a method that returned a reference to an object
52
The goal was to have a client call the method and receive back a reference to an object that implemented a given interface The client didn’t have to know exactly what kind of object was returned to it It was simply necessary that the object implemented the interface and agreed with type required by the client
53
Abstract Factories and Factory Method
The book has several examples and challenges From my point of view, the presentation is somewhat garbled and this makes it more difficult to see the pattern The remaining overheads for this chapter may be in book order in some places In other places, they may be rearranged and the explanations adjusted to fit my understanding of what’s going on
54
One of the reasons the presentation gets messy is that the book wants to separate classes into packages This isn’t a bad idea, and it’s a topic that isn’t covered in CS 201 and 202 It also hasn’t really been addressed in CS 304
55
However, the book starts dividing things up into packages at the same time it’s developing the example The final subsection in the chapter is about packages By the time you get to that section, most of what’s going to be done has already been done without very clear explanations
56
Factory Methods and Abstract Factory
The first thing to note about the next example is that its built on the factory method example In other words, an abstract factory can be described as a class containing a collection of factory methods
57
You may realize that you would like to apply the abstract factory pattern when several related factory methods arise in an application design The idea is that there is a group of related objects that need to be created and you put the methods for creating them together in a common class
58
Here is a thumbnail review of the factory method example
The CreditCheckFactory has a method createCreditCheck() that returns a reference to an object that implements the CreditCheck interface Two classes, CreditCheckOnline and CreditCheckOffline implement the interface
59
The code of the createCreditCheck() method knows which kind of object to create based on “server” code conditions Client code will receive a reference to one of the two different kinds of objects Client code doesn’t have to to specify or care which kind of object comes back The UML diagram for this is given on the next overhead
61
The book now adds things called billing checks and shipping checks to the credit check example
It doesn’t really explain what these things are, but it’s apparent that as checks, they are classified with credit checks
62
An intermediate UML diagram is given on the next overhead
It introduces the idea that you can start putting related things together in packages The diagram is intermediate because it doesn’t have enough information in it to show how it illustrates the abstract factory design pattern Specific comments on that will follow the diagram
64
In the preceding diagram there were two new classes, ShippingCheck and BillingCheck
Although they are checks of some sort, they don’t seem to be new types of credit checks They don’t implement the CreditCheck interface
65
Not surprisingly then, the CreditCheckFactory doesn’t have a method which constructs objects of these two new classes So the question remains, what are they exactly, and what role will they play in the abstract factory design pattern?
66
Another UML diagram is given on the following overhead
This is the book’s next step in explaining the design pattern—but it still doesn’t give the whole picture In this diagram, the checks have become interfaces Also, the CreditCheckFactory includes methods that return values that are of the types billing check, shipping check, and credit check
68
The preceding overhead was a UML diagram of the com. oozinoz
The preceding overhead was a UML diagram of the com.oozinoz.credit package, which contained these elements: A CreditCheck interface A CreditCheckOffline class that implements the interface Two more interfaces, BillingCheck and ShippingCheck A CreditCheckFactory class containing methods to create instances of each kind of check
69
Although it’s not possible to change what the book has done, it is worth noting the following:
In some sense, the example might be clearer and better if the CreditCheckFactory class were abstract This class turns out to be the “abstract” factory in the design being developed
70
Also notice that the design could not be fully functional as given so far
The return types for the methods of the CreditCheckFactory class are simply interface definitions No actual check classes are shown that could be constructed and returned
71
The book brings the example to completion in more or less the following way:
There will be no direct instances of the CreditCheckFactory class in the credit package There will be other packages, one for each country, such as the U.S. or Canada
72
In these packages there will be classes that implement the interfaces in the credit package
There will also be a factory class which extends the CreditCheckFactory class in the credit package The next overhead illustrates the relationship between the credit package and the Canada package
74
The Canada package contains live classes BillingCheckCanada, ShippingCheckCanada, and CreditCheckCanadaOnline which implement the check interfaces The package contains the CheckFactoryCanada class which extends the CreditCheckFactory class The contents of the CheckFactoryCanada class aren’t shown in detail in this diagram However, it will either inherit or override the methods which return either a billing check, a shipping check, or a credit check
75
Comment mode on: As noted earlier, I think the example would be better if the CreditCheckFactory class were abstract I also think it would be better if that class were renamed simply CheckFactory Billing and shipping checks don’t seem to be kinds of credit checks, but methods to create them are included in the factory
76
CreditCheckFactory only has the name it does because it was named before the example was expanded
Notice that the subclass is named CheckFactoryCanada, not CreditCheckFactoryCanada In other words, implicitly the authors recognize that at the implementation level this is a check factory, not a credit check factory Also, if you read the text closely, you’ll discover that at one point the authors refer to the CheckFactoryCanada class as a concrete factory, not an abstract factory
77
Continuing to Outline the Example
No separate package is given for the U.S., but conceptually the example is set up as if there would also be a concrete package for the U.S., analogous to the Canada package If set up as I would set it up, the credit package would contain an abstract check factory class and the two other packages would each contain a concrete check factory class that extended it
78
There is a reason that the CreditCheckOffline class in the credit class already is a concrete class that implements the CreditCheck interface The CreditCheckOffline is going to be the same for both Canada and the U.S. and can be shared by the code for both That can be taken care of with one implementing class in the parent package
79
The book says that the abstract factory pattern is like a collection of factory methods
It is after the U.S. package is added to the picture that this becomes apparent Take just createBillingCheck() for example
80
The return type of createBillingCheck() in the Canada package implementation will be BillingCheck
There would also be a separate implementation of the method in the U.S. package It would also return an object of type BillingCheck
81
Not only is the factory method at work because there are two kinds of credit check, online and offline The factory method is also at work because there are two kinds of billing check, Canadian and American There are different classes for each, but they both implement the common BillingCheck interface
82
There could be an additional layer of code on the server side of the example
That layer would contain if/else logic to determine whether a customer that a billing check was being run on was Canadian or American In other words, there might be a method whatKindOfCustomer() in this example That would be analogous to isAgencyUp() in the factory method example of the previous chapter
83
The actual kind of billing check object returned to a client would depend on the outcome of a call to whatKindOfCustomer() The ultimate client code would simply be handed a reference to an object that implemented the BillingCheck interface The client wouldn’t have to be aware or specifically request a billing check for one country or the other
84
The Implementation of the CheckFactoryCanada Class
Examining the code clarifies to a degree what is going on The only concrete method that would be necessary in the CreditCheckFactory class of the credit package would be isAgencyUp() The implementations of the methods in the CreateCheckCanada class that create checks would be country specific and override methods of the same name in the CreditCheckFactory class This is further evidence that the superclass should be abstract…
85
The book presents writing the code for CreateCheckCanada as challenge 17.4
The complete code is given on the following overheads
86
package com.oozinoz.ca;
import com.oozinoz.credit.*; public class CheckFactoryCanada extends CheckFactory { public BillingCheck createBillingCheck() return new BillingCheckCanada(); } public CreditCheck createCreditCheck() if(isAgencyUp()) return new CreditCheckCanadaOnline(); return new CreditCheckOffline(); public ShippingCheck createShippingCheck() return new ShippingCheckCanada();
87
Solution 17.4, book stuff continued
Your solution should Implement create- methods for methods inherited from the abstract CreditCheckFactory class Comment mode on: This indicates again what has gone wrong with the book example: They didn’t show that class and its methods as abstract in the UML diagram
88
Solution 17.4, book stuff continued
[Your solution should] Have the proper interface for the return type of each create- method Return a CreditCheckOffline object if the agency is down Comment mode on: This is obvious from the code already shown…
89
The UI Example vs. the Credit Check Example
After all this, if you’re still following my attempt to explain why the book’s presentation is muddled, consider these points In the UI example they had a concrete UI superclass for a given “standard” interface Then they added a concrete BetaUI subclass for an alternative interface
90
There was no literally abstract factory class in that example
It might have been better if they had had an abstract superclass with two concrete subclasses, UI and BetaUI
91
In the current, credit check example, they claim that there would be three packages: the credit package, the Canadian package, and a U.S. package They only show things for the credit and Canadian package
92
The credit package contains a concrete class, not an abstract class
This is what I think they did, probably unintentionally They started with a package that would have worked for the U.S. alone It would have contained concrete classes for shipping, billing, and credit checks It also would have contained a concrete factory class
93
In other words, the credit/U. S
In other words, the credit/U.S. factory class would have been analogous to the UI class in the previous example Then the Canadian factory class would have been analogous to the BetaUI class in the previous example They started changing over and only got halfway
94
They changed the checks to interfaces, but they left the concrete check factory (with its old name) in place If this explanation is correct, it’s understandable how the mix-up could occur Unfortunately, it makes things overall harder to sort out
95
Final note on this topic:
At one point in the previous materials the book referred to the CreateCheckCanada class as a concrete factory By the end of the chapter it’s back to referring to the pattern overall as abstract factory And as a consequence, even though the class in the Canadian package was concrete, it is referred to as an abstract factory class
96
Packages and Abstract Factories
The book now returns to the question of packages What more they actually have to say about packages is contained in the next challenge
97
Challenge 17.5 Write down an argument supporting the decision to place each factory and its related classes in a separate package. Or, argue that another approach is superior.
98
Solution 17.5 An example justification is: Placing country-specific classes in separate packages helps our Oozinoz developers to organize our software and our development efforts. By placing the classes for each country in a separate package, we keep country-specific packages independent of one another.
99
We can be confident, for example, that U. S
We can be confident, for example, that U.S.-specific classes have no impact on Canada-specific classes. We can also easily add support for new countries. For example, when we start doing business with Mexico, we can create a new package that provides the check services we need in a way that makes sense in that country.
100
This has the further advantage of letting us assign the credit
This has the further advantage of letting us assign the credit.mx package to a developer who has expertise in working with services and data from Mexico.
101
An argument against: Although this separation is nice in theory, it’s overwrought in practice. I’d rather have only one package with all the classes in it, at least until we expand to nine or ten countries. Spreading these classes over multiple packages winds up causing me three or more times the configuration-management work when I need to implement a change that cuts across all these packages.
102
Comment mode on: Eventually, as software grows, you may start to use packages If so, you’ll have to decide how to divide them up. When the time comes, you’ll have to make your own decision about the right approach
103
Summary What follows is a fairly faithful summary of what the book includes in the summary, interspersed with commentary The Abstract Factory pattern lets you arrange for a client to create objects that are part of a family of related dependent objects Comment mode on: It is clear from the examples that the objects are related The book hasn’t explained specifically what it means when it now says that they’re dependent
104
One example of related objects is groups of objects for different GUIs
Another example of related objects is groups of objects for different countries
105
As with Factory Method, Abstract Factory isolates clients from knowing which class to instantiate.
Comment mode on: This can be true, but the examples in this chapter didn’t grow to the point of illustrating it specifically For example, there was no server side code that checked which country a check request was being made for
106
Comment mode, continued:
Going back to the earlier example there was just one example of using an abstract factory It contained this call: JPanel panel = new Visualization(new BetaUI()); Whatever else you might say, it’s clear that this code had to specify which UI to use The only question is whether code of this form would appear on the client side or on the server side of the application overall
107
Comment mode, continued:
No example client code was given for the Canadian credit check example However, the situation is analogous to the previous one At some point a CheckFactoryCanada object would have to be created so that the unique implementations of the methods in it could be called The question is whether the creation of the object would be in client code or in server code
108
The End
Similar presentations
© 2025 SlidePlayer.com. Inc.
All rights reserved.