
- •CONTENTS
- •1.1 Introduction
- •1.2 What Is a Computer?
- •1.3 Programs
- •1.4 Operating Systems
- •1.5 Java, World Wide Web, and Beyond
- •1.6 The Java Language Specification, API, JDK, and IDE
- •1.7 A Simple Java Program
- •1.8 Creating, Compiling, and Executing a Java Program
- •1.9 (GUI) Displaying Text in a Message Dialog Box
- •2.1 Introduction
- •2.2 Writing Simple Programs
- •2.3 Reading Input from the Console
- •2.4 Identifiers
- •2.5 Variables
- •2.7 Named Constants
- •2.8 Numeric Data Types and Operations
- •2.9 Problem: Displaying the Current Time
- •2.10 Shorthand Operators
- •2.11 Numeric Type Conversions
- •2.12 Problem: Computing Loan Payments
- •2.13 Character Data Type and Operations
- •2.14 Problem: Counting Monetary Units
- •2.15 The String Type
- •2.16 Programming Style and Documentation
- •2.17 Programming Errors
- •2.18 (GUI) Getting Input from Input Dialogs
- •3.1 Introduction
- •3.2 boolean Data Type
- •3.3 Problem: A Simple Math Learning Tool
- •3.4 if Statements
- •3.5 Problem: Guessing Birthdays
- •3.6 Two-Way if Statements
- •3.7 Nested if Statements
- •3.8 Common Errors in Selection Statements
- •3.9 Problem: An Improved Math Learning Tool
- •3.10 Problem: Computing Body Mass Index
- •3.11 Problem: Computing Taxes
- •3.12 Logical Operators
- •3.13 Problem: Determining Leap Year
- •3.14 Problem: Lottery
- •3.15 switch Statements
- •3.16 Conditional Expressions
- •3.17 Formatting Console Output
- •3.18 Operator Precedence and Associativity
- •3.19 (GUI) Confirmation Dialogs
- •4.1 Introduction
- •4.2 The while Loop
- •4.3 The do-while Loop
- •4.4 The for Loop
- •4.5 Which Loop to Use?
- •4.6 Nested Loops
- •4.7 Minimizing Numeric Errors
- •4.8 Case Studies
- •4.9 Keywords break and continue
- •4.10 (GUI) Controlling a Loop with a Confirmation Dialog
- •5.1 Introduction
- •5.2 Defining a Method
- •5.3 Calling a Method
- •5.4 void Method Example
- •5.5 Passing Parameters by Values
- •5.6 Modularizing Code
- •5.7 Problem: Converting Decimals to Hexadecimals
- •5.8 Overloading Methods
- •5.9 The Scope of Variables
- •5.10 The Math Class
- •5.11 Case Study: Generating Random Characters
- •5.12 Method Abstraction and Stepwise Refinement
- •6.1 Introduction
- •6.2 Array Basics
- •6.3 Problem: Lotto Numbers
- •6.4 Problem: Deck of Cards
- •6.5 Copying Arrays
- •6.6 Passing Arrays to Methods
- •6.7 Returning an Array from a Method
- •6.8 Variable-Length Argument Lists
- •6.9 Searching Arrays
- •6.10 Sorting Arrays
- •6.11 The Arrays Class
- •7.1 Introduction
- •7.2 Two-Dimensional Array Basics
- •7.3 Processing Two-Dimensional Arrays
- •7.4 Passing Two-Dimensional Arrays to Methods
- •7.5 Problem: Grading a Multiple-Choice Test
- •7.6 Problem: Finding a Closest Pair
- •7.7 Problem: Sudoku
- •7.8 Multidimensional Arrays
- •8.1 Introduction
- •8.2 Defining Classes for Objects
- •8.3 Example: Defining Classes and Creating Objects
- •8.4 Constructing Objects Using Constructors
- •8.5 Accessing Objects via Reference Variables
- •8.6 Using Classes from the Java Library
- •8.7 Static Variables, Constants, and Methods
- •8.8 Visibility Modifiers
- •8.9 Data Field Encapsulation
- •8.10 Passing Objects to Methods
- •8.11 Array of Objects
- •9.1 Introduction
- •9.2 The String Class
- •9.3 The Character Class
- •9.4 The StringBuilder/StringBuffer Class
- •9.5 Command-Line Arguments
- •9.6 The File Class
- •9.7 File Input and Output
- •9.8 (GUI) File Dialogs
- •10.1 Introduction
- •10.2 Immutable Objects and Classes
- •10.3 The Scope of Variables
- •10.4 The this Reference
- •10.5 Class Abstraction and Encapsulation
- •10.6 Object-Oriented Thinking
- •10.7 Object Composition
- •10.8 Designing the Course Class
- •10.9 Designing a Class for Stacks
- •10.10 Designing the GuessDate Class
- •10.11 Class Design Guidelines
- •11.1 Introduction
- •11.2 Superclasses and Subclasses
- •11.3 Using the super Keyword
- •11.4 Overriding Methods
- •11.5 Overriding vs. Overloading
- •11.6 The Object Class and Its toString() Method
- •11.7 Polymorphism
- •11.8 Dynamic Binding
- •11.9 Casting Objects and the instanceof Operator
- •11.11 The ArrayList Class
- •11.12 A Custom Stack Class
- •11.13 The protected Data and Methods
- •11.14 Preventing Extending and Overriding
- •12.1 Introduction
- •12.2 Swing vs. AWT
- •12.3 The Java GUI API
- •12.4 Frames
- •12.5 Layout Managers
- •12.6 Using Panels as Subcontainers
- •12.7 The Color Class
- •12.8 The Font Class
- •12.9 Common Features of Swing GUI Components
- •12.10 Image Icons
- •13.1 Introduction
- •13.2 Exception-Handling Overview
- •13.3 Exception-Handling Advantages
- •13.4 Exception Types
- •13.5 More on Exception Handling
- •13.6 The finally Clause
- •13.7 When to Use Exceptions
- •13.8 Rethrowing Exceptions
- •13.9 Chained Exceptions
- •13.10 Creating Custom Exception Classes
- •14.1 Introduction
- •14.2 Abstract Classes
- •14.3 Example: Calendar and GregorianCalendar
- •14.4 Interfaces
- •14.5 Example: The Comparable Interface
- •14.6 Example: The ActionListener Interface
- •14.7 Example: The Cloneable Interface
- •14.8 Interfaces vs. Abstract Classes
- •14.9 Processing Primitive Data Type Values as Objects
- •14.10 Sorting an Array of Objects
- •14.11 Automatic Conversion between Primitive Types and Wrapper Class Types
- •14.12 The BigInteger and BigDecimal Classes
- •14.13 Case Study: The Rational Class
- •15.1 Introduction
- •15.2 Graphical Coordinate Systems
- •15.3 The Graphics Class
- •15.4 Drawing Strings, Lines, Rectangles, and Ovals
- •15.5 Case Study: The FigurePanel Class
- •15.6 Drawing Arcs
- •15.7 Drawing Polygons and Polylines
- •15.8 Centering a String Using the FontMetrics Class
- •15.9 Case Study: The MessagePanel Class
- •15.10 Case Study: The StillClock Class
- •15.11 Displaying Images
- •15.12 Case Study: The ImageViewer Class
- •16.1 Introduction
- •16.2 Event and Event Source
- •16.3 Listeners, Registrations, and Handling Events
- •16.4 Inner Classes
- •16.5 Anonymous Class Listeners
- •16.6 Alternative Ways of Defining Listener Classes
- •16.7 Problem: Loan Calculator
- •16.8 Window Events
- •16.9 Listener Interface Adapters
- •16.10 Mouse Events
- •16.11 Key Events
- •16.12 Animation Using the Timer Class
- •17.1 Introduction
- •17.2 Buttons
- •17.3 Check Boxes
- •17.4 Radio Buttons
- •17.5 Labels
- •17.6 Text Fields
- •17.7 Text Areas
- •17.8 Combo Boxes
- •17.9 Lists
- •17.10 Scroll Bars
- •17.11 Sliders
- •17.12 Creating Multiple Windows
- •18.1 Introduction
- •18.2 Developing Applets
- •18.3 The HTML File and the <applet> Tag
- •18.4 Applet Security Restrictions
- •18.5 Enabling Applets to Run as Applications
- •18.6 Applet Life-Cycle Methods
- •18.7 Passing Strings to Applets
- •18.8 Case Study: Bouncing Ball
- •18.9 Case Study: TicTacToe
- •18.10 Locating Resources Using the URL Class
- •18.11 Playing Audio in Any Java Program
- •18.12 Case Study: Multimedia Animations
- •19.1 Introduction
- •19.2 How is I/O Handled in Java?
- •19.3 Text I/O vs. Binary I/O
- •19.4 Binary I/O Classes
- •19.5 Problem: Copying Files
- •19.6 Object I/O
- •19.7 Random-Access Files
- •20.1 Introduction
- •20.2 Problem: Computing Factorials
- •20.3 Problem: Computing Fibonacci Numbers
- •20.4 Problem Solving Using Recursion
- •20.5 Recursive Helper Methods
- •20.6 Problem: Finding the Directory Size
- •20.7 Problem: Towers of Hanoi
- •20.8 Problem: Fractals
- •20.9 Problem: Eight Queens
- •20.10 Recursion vs. Iteration
- •20.11 Tail Recursion
- •APPENDIXES
- •INDEX

14.7 Example: The Cloneable Interface 471
actionPerformed(ActionEvent) method (line 42) in CancelListenerClass is invoked to process the event. Ways to process events will be discussed further in Chapter 16, “Event-Driven Programming.”
14.7 Example: The Cloneable Interface
Often it is desirable to create a copy of an object. You need to use the clone method and understand the Cloneable interface, which is the subject of this section.
An interface contains constants and abstract methods, but the Cloneable interface is a special case. The Cloneable interface in the java.lang package is defined as follows:
package java.lang; |
java.lang.Cloneable |
public interface Cloneable {
}
This interface is empty. An interface with an empty body is referred to as a marker interface. marker interface A marker interface does not contain constants or methods. It is used to denote that a class pos-
sesses certain desirable properties. A class that implements the Cloneable interface is marked cloneable, and its objects can be cloned using the clone() method defined in the
Object class.
Many classes in the Java library (e.g., Date, Calendar, and ArrayList) implement Cloneable. Thus, the instances of these classes can be cloned. For example, the following code
1 Calendar calendar = new GregorianCalendar(2003, 2, 1); 2 Calendar calendar1 = calendar;
3 Calendar calendar2 = (Calendar)calendar.clone();
4 System.out.println("calendar == calendar1 is " +
5(calendar == calendar1));
6 System.out.println("calendar == calendar2 is " +
7(calendar == calendar2));
8 System.out.println("calendar.equals(calendar2) is " +
9 calendar.equals(calendar2));
displays
calendar == calendar1 is true calendar == calendar2 is false calendar.equals(calendar2) is true
In the preceding code, line 2 copies the reference of calendar to calendar1, so |
|
|
calendar and calendar1 point to the same Calendar object. Line 3 creates a new object |
|
|
that is the clone of calendar and assigns the new object’s reference to calendar2. |
|
|
calendar2 and calendar are different objects with the same contents. |
|
|
You can clone an array using the clone method. For example, the following code |
clone arrays |
|
1 |
int[] list1 = {1, 2}; |
|
2 |
int[] list2 = list1.clone(); |
|
3 |
list1[0] = 7; list1[1] = 8; |
|
4 |
|
|
5 |
System.out.println("list1 is " + list1[0] + ", " + list1[1]); |
|
6 |
System.out.println("list2 is " + list2[0] + ", " + list2[1]); |
|
displays
list1 is 7, 8 list2 is 1, 2

472 Chapter 14 Abstract Classes and Interfaces
how to implement |
To define a custom class that implements the Cloneable interface, the class must override |
Cloneable |
the clone() method in the Object class. Listing 14.9 defines a class named House that |
|
implements Cloneable and Comparable. |
LISTING 14.9 House.java
|
1 |
public class |
House implements Cloneable, Comparable |
{ |
|||||
|
2 |
|
private int id; |
||||||
|
3 |
|
private double area; |
||||||
|
4 |
|
private java.util.Date whenBuilt; |
||||||
|
5 |
|
|
|
|
|
|
|
|
|
6 |
|
public House(int id, double area) { |
||||||
|
7 |
|
|
this.id = id; |
|||||
|
8 |
|
|
this.area = area; |
|||||
|
9 |
|
|
whenBuilt = new java.util.Date(); |
|||||
|
10 |
} |
|
|
|
|
|
|
|
|
11 |
|
|
|
|
|
|
|
|
|
12 |
|
public int getId() { |
||||||
|
13 |
|
|
return id; |
|||||
|
14 |
} |
|
|
|
|
|
|
|
|
15 |
|
|
|
|
|
|
|
|
|
16 |
|
public double getArea() { |
||||||
|
17 |
|
|
return area; |
|||||
|
18 |
} |
|
|
|
|
|
|
|
|
19 |
|
|
|
|
|
|
|
|
|
20 |
|
public java.util.Date getWhenBuilt() { |
||||||
|
21 |
|
|
return whenBuilt; |
|||||
|
22 |
} |
|
|
|
|
|
|
|
|
23 |
|
|
|
|
|
|
|
|
|
24 |
|
/** Override the protected clone method defined in the Object |
||||||
|
25 |
|
|
class, and strengthen its accessibility */ |
|||||
This exception is thrown if |
26 |
|
public Object clone() |
throws CloneNotSupportedException { |
|||||
House does not implement |
27 |
|
|
return super.clone(); |
|
|
|||
Cloneable |
28 |
} |
|
|
|
|
|
|
|
|
29 |
|
|
|
|
|
|
|
|
|
30 |
|
/** Implement the compareTo method defined in Comparable */ |
||||||
|
31 |
|
public int compareTo(Object o) { |
|
|
||||
|
32 |
|
|
if (area > ((House)o).area) |
|||||
|
33 |
|
|
return 1; |
|||||
|
34 |
|
|
else if (area < ((House)o).area) |
|||||
|
35 |
|
|
return -1; |
|||||
|
36 |
|
|
else |
|||||
|
37 |
|
|
return 0; |
|||||
|
38 |
} |
|
|
|
|
|
|
|
|
39 |
} |
|
|
|
|
|
|
|
CloneNotSupported-
Exception
The House class implements the clone method (lines 26–28) defined in the Object class. The header is:
protected native Object clone() throws CloneNotSupportedException;
The keyword native indicates that this method is not written in Java but is implemented in the JVM for the native platform. The keyword protected restricts the method to be accessed in the same package or in a subclass. For this reason, the House class must override the method and change the visibility modifier to public so that the method can be used in any package. Since the clone method implemented for the native platform in the Object class performs the task of cloning objects, the clone method in the House class simply invokes super.clone(). The clone method defined in the Object class may throw
CloneNotSupportedException.

14.8 Interfaces vs. Abstract Classes 473
The House class implements the compareTo method (lines 31–38) defined in the Comparable interface. The method compares the areas of two houses.
You can now create an object of the House class and create an identical copy from it, as follows:
House house1 = new House(1, 1750.50);
House house2 = (House)house1.clone();
house1 and house2 are two different objects with identical contents. The clone method in |
|
|||||||||||||||||
the Object class copies each field from the original object to the target object. If the field is of |
|
|||||||||||||||||
a primitive type, its value is copied. For example, the value of area (double type) is copied |
|
|||||||||||||||||
from house1 to house2. If the field is of an object, the reference of the field is copied. For |
|
|||||||||||||||||
example, the field whenBuilt is of the Date class, so its reference is copied into house2, as |
|
|||||||||||||||||
shown in Figure 14.6. Therefore, house1.whenBuilt == house2.whenBuilt is true, |
|
|||||||||||||||||
although house1 == house2 is false. This is referred to as a shallow copy rather than a deep |
shallow copy |
|||||||||||||||||
copy, meaning that if the field is of an object type, the object’s reference is copied rather than |
deep copy |
|||||||||||||||||
its contents. |
|
|
|
|
|
|
|
|
|
|
||||||||
|
house1: House |
|
|
Memory |
|
|
|
|
||||||||||
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
id = 1 |
|
|
|
|
|
|
1 |
|
|
|
|
|
|
|
|||
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|||||
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
area = 1750.50 |
|
|
|
1750.50 |
|
|
|
|
|
whenBuilt: Date |
|
||||||
|
|
|
|
|
|
|
|
|
|
|||||||||
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
whenBuilt |
|
|
|
|
|
reference |
|
|
|
|
|
|
|||||
|
|
|
|
|
|
|
|
|||||||||||
house2 = house1.clone() |
|
|
|
|
|
|
|
|
|
date object contents |
|
|||||||
|
|
|
|
|
|
|
|
|||||||||||
|
|
|
|
|
|
|
|
|
|
|
||||||||
|
house2: House |
|
|
Memory |
|
|
|
|
||||||||||
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
id = 1 |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
||
|
|
|
|
|
1 |
|
|
|
|
|
|
|
||||||
|
|
|
|
|
|
|
|
|
|
|
|
|||||||
|
area = 1750.50 |
|
|
|
|
|
|
|
|
|
|
|
|
|
||||
|
|
|
|
1750.50 |
|
|
|
|
|
|
|
|||||||
|
|
|
|
|
|
|
|
|
|
|
||||||||
|
whenBuilt |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
||
|
|
|
|
|
reference |
|
|
|
|
|
|
|||||||
|
|
|
|
|
|
|
|
|
|
|
FIGURE 14.6 The clone method copies the values of primitive type fields and the references of object type fields.
If you want to perform a deep copy, you can override the clone method with custom cloning operations after invoking super.clone(). See Exercise 14.4.
Caution
If the House class does not override the clone() method, the program will receive a syntax error, because clone() is protected in java.lang.Object. If House does not implement java.lang.Cloneable, invoking super.clone() (line 27) in House.java will cause a CloneNotSupportedException. Thus, to enable cloning an object, the class for the object must override the clone() method and implement Cloneable.
14.8 Interfaces vs. Abstract Classes
An interface can be used more or less the same way as an abstract class, but defining an interface is different from defining an abstract class. Table 14.2 summarizes the differences.
Java allows only single inheritance for class extension but allows multiple extensions for interfaces. For example,

474 Chapter 14 Abstract Classes and Interfaces |
|
|
||
|
TABLE 14.2 Interfaces vs. Abstract Classes |
|
||
|
|
|
|
|
|
|
Variables |
Constructors |
Methods |
|
|
|
|
|
|
Abstract class |
No restrictions. |
Constructors are invoked by |
No restrictions. |
|
|
|
subclasses through constructor |
|
|
|
|
chaining. An abstract class |
|
|
|
|
cannot be instantiated using |
|
|
|
|
the new operator. |
|
|
Interface |
All variables must be |
No constructors. An interface |
All methods must be |
|
|
public static |
cannot be instantiated using |
public abstract |
|
|
final. |
the new operator. |
instance methods. |
|
public class NewClass |
extends |
BaseClass |
||||||
|
|
implements |
Interface1, ..., InterfaceN { |
||||||
|
... |
|
|
|
|
|
|
|
|
|
} |
|
|
|
|
|
|
|
|
|
An interface can inherit other interfaces using the extends keyword. Such an interface is |
||||||||
subinterface |
called a subinterface. For example, NewInterface in the following code is a subinterface of |
||||||||
|
Interface1, Á , and InterfaceN. |
||||||||
|
|
|
|
|
|
|
|
||
|
public |
interface |
NewInterface |
extends |
Interface1, ..., InterfaceN { |
||||
|
// constants and abstract methods |
||||||||
|
} |
|
|
|
|
|
|
|
|
|
A class implementing NewInterface must implement the abstract methods defined |
||||||||
|
in NewInterface, Interface1, Á , and InterfaceN. An interface can extend other |
||||||||
|
interfaces but not classes. A class can extend its superclass and implement multiple |
||||||||
|
interfaces. |
||||||||
|
All classes share a single root, the Object class, but there is no single root for interfaces. |
||||||||
|
Like a class, an interface also defines a type. A variable of an interface type can reference any |
||||||||
|
instance of the class that implements the interface. If a class implements an interface, the |
||||||||
|
interface is like a superclass for the class. You can use an interface as a data type and cast a |
||||||||
|
variable of an interface type to its subclass, and vice versa. For example, suppose that c is an |
||||||||
|
instance of Class2 in Figure 14.7. c is also an instance of Object, Class1, Interface1, |
Interface1_1, Interface1_2, Interface2_1, and Interface2_2.
Interface1_2 |
Interface2_2 |
Interface1_1 |
Interface1 |
Interface2_1 |
Object |
Class1 |
Class2 |
FIGURE 14.7 Class1 implements Interface1; Interface1 extends Interface1_1 and Interface1_2. Class2 extends Class1 and implements Interface2_1 and Interface2_2.

14.8 Interfaces vs. Abstract Classes 475
Note
Class names are nouns. Interface names may be adjectives or nouns. For example, both |
naming convention |
java.lang.Comparable and java.awt.event.ActionListener are interfaces. |
|
Comparable is an adjective, and ActionListener is a noun. |
|
Design Guide
Abstract classes and interfaces can both be used to specify common behavior of objects. How do |
|
you decide whether to use an interface or a class? In general, a strong is-a relationship that clearly |
|
describes a parent-child relationship should be modeled using classes. For example, Gregorian cal- |
|
endar is a calendar, so the relationship between the class java.util.GregorianCalendar |
|
and java.util.Calendar is modeled using class inheritance. A weak is-a relationship, also |
is-a relationship |
known as an is-kind-of relationship, indicates that an object possesses a certain property. A weak |
is-kind-of relationship |
is-a relationship can be modeled using interfaces. For example, all strings are comparable, so the |
|
String class implements the Comparable interface. |
|
In general, interfaces are preferred over abstract classes because an interface can define a |
interface preferred |
||||
common supertype for unrelated classes. Interfaces are more flexible than classes. Consider |
|
||||
the Animal class. Suppose the howToEat method is defined in the Animal class, as follows: |
|
||||
abstract class Animal { |
|
||||
|
public abstract String howToEat() |
; |
Animal class |
||
} |
|
|
|
|
|
Two subclasses of Animal are defined as follows: |
|
||||
class Chicken extends Animal { |
Chicken class |
||||
|
public String howToEat() |
{ |
|
|
|
|
return "Fry it"; |
|
|||
} |
|
|
|
|
|
} |
|
|
|
|
|
class Duck extends Animal { |
Duck class |
||||
|
public String howToEat() |
{ |
|
|
|
|
return "Roast it"; |
|
|||
} |
|
|
|
|
|
} |
|
|
|
|
|
Given this inheritance hierarchy, polymorphism enables you to hold a reference to a Chicken object or a Duck object in a variable of type Animal, as in the following code:
public static void main(String[] args) { Animal animal = new Chicken(); eat(animal);
animal = new Duck(); eat(animal);
}
public static void eat(Animal animal) { animal.howToEat();
}
The JVM dynamically decides which howToEat method to invoke based on the actual object that invokes the method.
You can define a subclass of Animal. However, there is a restriction. The subclass must be for another animal (e.g., Turkey).
Interfaces don’t have this restriction. Interfaces give you more flexibility than classes, because you don’t have make everything fit into one type of class. You may define the