...
An abstract class cannot be instantiated but it can be extended, that it, you cannot create an object of an abstract class but other classes can in-herit from it. Abstract classes can have concrete data and methods, which perform normally.
Programming with abstract classes
Suppose that you were commissioned to develop a program for operating a pet shop which sells dogs, cats, and birds to the public. The owner needs to identify each animal that is available and keep track of its location and sale price. Specifically, the owner also wants to keep track of each dog and cat breed, and of the color of each bird. There is a plan to add other pet species at a future date, so the system should be easily expandable. After analyzing the software requirement you propose the following data elements:
1. Each pet is given a name, which is remembered in a string variable.
2. Each pet has a sale price, stored in a variable of type double.
3. A variable of type int keeps track of the location of each pet in the store. The pet store showroom is location 1, the backroom is location 2, and the store's basement is location 3.
4. There is also species-specific data that must be remembered: the breed of each dog, the breed of each cat, and the color of each bird.
Since a dog is a kind of a pet, and so is a cat and a bird, you can use in-heritance to model the pet store system. A base class named Pet could be used to define the data elements that are common to all three pet species.
Since the notion of a pet is an abstraction, the class Pet is defined as an abstract class. The Pet class also defines the interface for the methods that are implemented in the subclasses. The class diagram for the pet store is shown inFigure 16-4.
Figure 16-4 Class Diagram for the Pet Store System Pet
petName petLocation petPrice
getName() getLocation() getPrice() getSpecData()
getSpecData() getSpecData() getSpecData()
dogBreed catBreed birdColor
Dog Cat Bird
The implementation of the PetStore system is based on the class dia-gram inFigure 16-4. The class Pet holds variables for the name, location, and price of all pets in the store. It also contains three concrete methods to display the name, location, and price of each pet object. In order to preserve encapsulation, the accessor methods for the class-level attrib-utes must be in the superclass. Recall that, with or without inheritance, private data is not visible outside the class.
In addition, the superclass Pet contains an abstract method named getSpecData(). The getSpecData() method is implemented in each of the subclasses. In the Dog class, getSpecData() displays the dogBreed. In the Cat class, getSpecData() displays the cat name. In the Bird class, getSpecData() displays the bird color. The following code listing is for the PetStore program.
On the Web
The program PetStore is found in the Chapter 16 folder at www.crcpress.com.
//**********************************************************
//**********************************************************
// Program: PetStore // Reference: Chapter 16 // Topics:
// 1. Using inheritance and abstract classes
//**********************************************************
// Defines the initial pet state
public Pet(String name, int location, double price)
// Concrete methods in the base class public void getName()
{
System.out.println ("Pet name: " + this.petName);
return;
}
public void getLocation() {
System.out.println("Pet location: " + this.petLocation);
return;
}
public void getPrice() {
System.out.println("Pet price: " + this.petPrice);
return;
}
// Abstract method
public abstract void getSpecData();
j}
//************************************
// concrete classes
//************************************
class Dog extends Pet {
// Data specific for the Dog class String dogBreed;
int dogAge;
// Constructor for the Dog class uses the constructor // if the superclass
public Dog(String name, int loc, double price, String race) {
// Call the constructor in Pet super(name, loc, price);
// Fill-in the dog-specific data this.dogBreed = race;
}
// Concrete methods in subclass public void getSpecData() {
System.out.println("Dog race :" + this.dogBreed);
return;
} }
class Cat extends Pet {
// Data specific for the Cat class String catBreed;
public Cat(String name, int loc, double price, String race) {
// Call the constructor in Pet super(name, loc, price);
// Fill-in the cat-specific data this.catBreed = race;
}
// Concrete methods in subclass public void getSpecData() {
System.out.println("Cat race: " + this.catBreed);
return;
} }
class Bird extends Pet {
// Data specific for the Cat class String birdColor;
public Bird(String name, int loc, double price, String color) {
// Call the constructor in Pet super(name, loc, price);
// Fill-in the cat-specific data this.birdColor = color;
}
// Concrete methods in subclass public void getSpecData() {
System.out.println("Bird color: " + this.birdColor);
return;
public static void main(String[] args) {
// Create two objects of class Dog
Dog dog1 = new Dog("Fido",2, 12.95,"Spaniel");
Dog dog2 = new Dog("Atila",3, 20.75,"Hound");
// Create a Cat and a Bird object
Cat cat1 = new Cat("Fifo", 3, 15.95, "Siamese");
Bird bird1 = new Bird("Tweety", 1, 2.55, "Yellow");
// Display pet data using superclass and subclass // methods
dog1.getName(); // Method in superclass dog2.getName(); // Methods in superclass dog2.getLocation();
dog2.getSpecData(); // Method in subclass bird1.getName();
bird1.getSpecData();
} }
Do not assume that an abstract class should only have abstract meth-ods. The general rule is to have as much functionality as possible in the superclass, whether or not it is an abstract class. Instance fields and non-abstract methods should all be in the superclass. Operations that cannot be implemented in the superclass are the only ones that should be in the subclasses. This approach is the one used in the PetStore program listed previously.
One of the advantages of using inheritance is greater code reusability.
Suppose that the pet store owner decided to expand the store line to in-clude pet lizards. In this case the functionality for keeping track of the name, location, and price of each pet lizard is already in place. The PetStore program could be easily modified by implementing a new class called Lizard, that extends Pet. Only the data and operations that are spe-cific for each pet lizard would have to be implemented in the new class.