In the "Software Engineering Case Study" sections in Chapters 17, we introduced the fundamentals of object orientation and developed an object-oriented design for our ATM system. Earlier in this chapter, we discussed many of the details of programming with Java classes. We now begin implementing our object-oriented design in Java. At the end of this section, we show how to convert class diagrams to Java code. In the final "Software Engineering Case Study" section (Section 10.9), we modify the code to incorporate the object-oriented concept of inheritance. We present the full Java code implementation in Appendix J.
Visibility
We now apply access modifiers to the members of our classes. In Chapter 3, we introduced access modifiers public and private. Access modifiers determine the visibility or accessibility of an object's attributes and methods to other objects. Before we can begin implementing our design, we must consider which attributes and methods of our classes should be public and which should be private.
In Chapter 3, we observed that attributes normally should be private and that methods invoked by clients of a given class should be public. Methods that are called only by other methods of the class as "utility methods," however, normally should be private. The UML employs visibility markers for modeling the visibility of attributes and operations. Public visibility is indicated by placing a plus sign (+) before an operation or an attribute, whereas a minus sign () indicates private visibility. Figure 8.24 shows our updated class diagram with visibility markers included. [Note: We do not include any operation parameters in Fig. 8.24this is perfectly normal. Adding visibility markers does not affect the parameters already modeled in the class diagrams of Fig. 6.22Fig. 6.25.]
Figure 8.24. Class diagram with visibility markers.
(This item is displayed on page 402 in the print version)
Navigability
Before we begin implementing our design in Java, we introduce an additional UML notation. The class diagram in Fig. 8.25 further refines the relationships among classes in the ATM system by adding navigability arrows to the association lines. Navigability arrows (represented as arrows with stick arrowheads in the class diagram) indicate in which direction an association can be traversed. When implementing a system designed using the UML, programmers use navigability arrows to help determine which objects need references to other objects. For example, the navigability arrow pointing from class ATM to class BankDatabase indicates that we can navigate from the former to the latter, thereby enabling the ATM to invoke the BankDatabase's operations. However, since Fig. 8.25 does not contain a navigability arrow pointing from class BankDatabase to class ATM, the BankDatabase cannot access the ATM's operations. Note that associations in a class diagram that have navigability arrows at both ends or do not have navigability arrows at all indicate bidirectional navigabilitynavigation can proceed in either direction across the association.
Figure 8.25. Class diagram with navigability arrows.
(This item is displayed on page 403 in the print version)
Like the class diagram of Fig. 3.24, the class diagram of Fig. 8.25 omits classes BalanceInquiry and Deposit to keep the diagram simple. The navigability of the associations in which these classes participate closely parallels the navigability of class Withdrawal. Recall from Section 3.10 that BalanceInquiry has an association with class Screen. We can navigate from class BalanceInquiry to class Screen along this association, but we cannot navigate from class Screen to class BalanceInquiry. Thus, if we were to model class BalanceInquiry in Fig. 8.25, we would place a navigability arrow at class Screen's end of this association. Also recall that class Deposit associates with classes Screen, Keypad and DepositSlot. We can navigate from class Deposit to each of these classes, but not vice versa. We therefore would place navigability arrows at the Screen, Keypad and DepositSlot ends of these associations. [Note: We model these additional classes and associations in our final class diagram in Section 10.9, after we have simplified the structure of our system by incorporating the object-oriented concept of inheritance.]
Implementing the ATM System from Its UML Design
We are now ready to begin implementing the ATM system. We first convert the classes in the diagrams of Fig. 8.24 and Fig. 8.25 into Java code. The code will represent the "skeleton" of the system. In Chapter 10, we modify the code to incorporate the object-oriented concept of inheritance. In Appendix J, ATM Case Study Code, we present the complete working Java code for our model.
As an example, we develop the code from our design of class Withdrawal in Fig. 8.24. We use this figure to determine the attributes and operations of the class. We use the UML model in Fig. 8.25 to determine the associations among classes. We follow the following four guidelines for each class:
Figure 8.26. Java code for class Withdrawal based on Fig. 8.24 and Fig. 8.25.
1 // Class Withdrawal represents an ATM withdrawal transaction 2 public class Withdrawal 3 { 4 // no-argument constructor 5 public Withdrawal() 6 { 7 } // end no-argument Withdrawal constructor 8 } // end class Withdrawal |
Figure 8.27. Java code for class Withdrawal based on Fig. 8.24 and Fig. 8.25.
1 // Class Withdrawal represents an ATM withdrawal transaction 2 public class Withdrawal 3 { 4 // attributes 5 private int accountNumber; // account to withdraw funds from 6 private double amount; // amount to withdraw 7 8 // no-argument constructor 9 public Withdrawal() 10 { 11 } // end no-argument Withdrawal constructor 12 } // end class Withdrawal |
Figure 8.28. Java code for class Withdrawal based on Fig. 8.24 and Fig. 8.25.
(This item is displayed on page 405 in the print version)
1 // Class Withdrawal represents an ATM withdrawal transaction 2 public class Withdrawal 3 { 4 // attributes 5 private int accountNumber; // account to withdraw funds from 6 private double amount; // amount to withdraw 7 8 // references to associated objects 9 private Screen screen; // ATM's screen 10 private Keypad keypad; // ATM's keypad 11 private CashDispenser cashDispenser; // ATM's cash dispenser 12 private BankDatabase bankDatabase; // account info database 13 14 // no-argument constructor 15 public Withdrawal() 16 { 17 } // end no-argument Withdrawal constructor 18 } // end class Withdrawal |
Figure 8.29. Java code for class Withdrawal based on Fig. 8.24 and Fig. 8.25.
(This item is displayed on page 405 in the print version)
1 // Class Withdrawal represents an ATM withdrawal transaction 2 public class Withdrawal 3 { 4 // attributes 5 private int accountNumber; // account to withdraw funds from 6 private double amount; // amount to withdraw 7 8 // references to associated objects 9 private Screen screen; // ATM's screen 10 private Keypad keypad; // ATM's keypad 11 private CashDispenser cashDispenser; // ATM's cash dispenser 12 private BankDatabase bankDatabase; // account info database 13 14 // no-argument constructor 15 public Withdrawal() 16 { 17 } // end no-argument Withdrawal constructor 18 19 // operations 20 public void execute() 21 { 22 } // end method execute 23 } // end class Withdrawal |
This concludes our discussion of the basics of generating classes from UML diagrams.
Software Engineering Case Study Self-Review Exercises
8.1 |
State whether the following statement is true or false, and if false, explain why: If an attribute of a class is marked with a minus sign (-) in a class diagram, the attribute is not directly accessible outside of the class. |
8.2 |
In Fig. 8.25, the association between the ATM and the Screen indicates that:
|
8.3 |
Write Java code to begin implementing the design for class Keypad. |
Answers to Software Engineering Case Study Self-Review Exercises
8.1 |
True. The minus sign () indicates private visibility. |
|
8.2 |
b. |
|
8.3 |
The design for class Keypad yields the code in Fig. 8.30. Recall that class Keypad has no attributes for the moment, but attributes may become apparent as we continue the implementation. Also note that if we were designing a real ATM, method getInput would need to interact with the ATM's keypad hardware. We will actually do input from the keyboard of a personal computer when we write the complete Java code in Appendix J. Figure 8.30. Java code for class Keypad based on Fig. 8.24 and Fig. 8.25.
|
Introduction to Computers, the Internet and the World Wide Web
Introduction to Java Applications
Introduction to Classes and Objects
Control Statements: Part I
Control Statements: Part 2
Methods: A Deeper Look
Arrays
Classes and Objects: A Deeper Look
Object-Oriented Programming: Inheritance
Object-Oriented Programming: Polymorphism
GUI Components: Part 1
Graphics and Java 2D™
Exception Handling
Files and Streams
Recursion
Searching and Sorting
Data Structures
Generics
Collections
Introduction to Java Applets
Multimedia: Applets and Applications
GUI Components: Part 2
Multithreading
Networking
Accessing Databases with JDBC
Servlets
JavaServer Pages (JSP)
Formatted Output
Strings, Characters and Regular Expressions
Appendix A. Operator Precedence Chart
Appendix B. ASCII Character Set
Appendix C. Keywords and Reserved Words
Appendix D. Primitive Types
Appendix E. (On CD) Number Systems
Appendix F. (On CD) Unicode®
Appendix G. Using the Java API Documentation
Appendix H. (On CD) Creating Documentation with javadoc
Appendix I. (On CD) Bit Manipulation
Appendix J. (On CD) ATM Case Study Code
Appendix K. (On CD) Labeled break and continue Statements
Appendix L. (On CD) UML 2: Additional Diagram Types
Appendix M. (On CD) Design Patterns
Appendix N. Using the Debugger
Inside Back Cover