CSC 207 Grinnell College Spring, 2012
 
Algorithms and Object-Oriented Design
 

Single Inheritance, Multiple Inheritance, and Generics

Summary

This reading supplements the textbook in reviewing the high-level concepts of single and multiple inheritance and Java's perspective on Generics.

Introduction

Consider the following Java-class hierarchy for a general Grinnell College course and a computer science course at Grinnell.

cs-course-2

Conceptually, this hierarchy makes logical sense:

We now consider practical issues of this hierarchy of classes in Java.

A Grinnell Course Class

Most fields for a Grinnell Course can follow a similar approach as the first Course class that we discussed on the first day of CSC 2007. In particular, a department, title, instructor, and room can be Strings, and a course number and credits can be ints. However, the prerequisite list needs to be a collection of courses — perhaps a list of Strings.

One way to proceed would be to implement our own array or list structure. However, Java contains an extensive library, and we can save substantial time by using this library. For example, Java contains a general notion of a List. A review of the List specification raises two new issues:

Generics

To resolve the first issue (specific data types within a List, Java utilizes the concept of generics. The description of a List begins

   Interface List <E>

Ignoring the word Interface for a moment, the syntax <E> allows us to identify the prerequisite list as a list of strings:

   List <String> prerequisiteList = ...

In another setting, the variable could be

   List <Course> courseList = ...
   List <Integer> numberList = ...

List Implementations

Although a List identifies capabilities, a List does not actually have any details. In the jargon of Java, a List is an Interface — a statement of required methods but NO field or method details. (This explains the term Interface in the Java API specification for a List.

One widely-used implementation of the List interface is the ArrayList. With this implementation, a programmer can create an indexed data structure, much like an array; that is, the programmer can add items at the start or the structure, the end of the structure, or anywhere in the middle. Behind the scenes, the ArrayList keeps track of the size of an array needed to store the desired items, and the ArrayList resizes itself whenever more space is needed.

Note that an ArrayList is also an generic class, so different ArrayLists may store different types of objects. Thus, the following declarations could be used to declare a variety of lists:

   List <String> prerequisiteList = new ArrayList <String> ;
   List <Course> courseList = new ArrayList <Course> ;
   List <Integer> numberList = new ArrayList <Integer> ;

Altogether, an ArrayList provides an appropriate way to work with a prerequisiteList for a Grinnell College course, and we can write a complete GrinnellCollege class.

Note the "enhanced for" loop for iterating through a List structure.

CC2008

Although conceptually CC2008 is just another class in our diagram, allowing GrinnellCSCourses to inherit from both GrinnellCourse and CC2008 has several potential problems. In particular, if both GrinnellCourse and CC2008 had different implementations of a method, rules would be needed to determine which version to use. This situation is called "multiple inheritance", and resolving duplicate naming issues can be very complex. For example, in the C++ language which allows multiple inheritance, an extensive collection of complex rules govern how inheritance works within an extensive class hierarchy.

Rather than allow complex inheritance rules, Java allows a class to inherit directly from only one class (although that class in turn can inherit from one class higher in the hierarchy). However, Java also defines an Interface that identifies method names without any implementation details. A class can implement as many Interfaces as desired, but the class will need to provide implementation details for each method in the Interface.

The List class is one example of such an Interface. Since we want a GrinnellCSCourseto be both a GrinnellCourse and a CC2008, we will specify CC2008 as an Interface.

The formal code for CC2008 looks quite similar to a stripped-down class definition; the signatures of all methods are specified, but no details for fields or methods are given. The complete Interface definition for CC2008 identifies all relevant methods without providing any implementation details.

The GrinnellCSCourse Class

With GrinnellCourse and CC2008 defined, we can define GrinnellCSCourse. In particular, GrinnellCSCourse extends GrinnellCourse, as we have seen with other subclasses. In working with CC2008, Java specifies that a class implements an Interface. The start of the class is

   public class GrinnellCSCourse extends GrinnellCourse
          implements CC2008 { 
    ...

Adding details then proceeds for implementing interfaces in the same way as extending a class, except that a complete class must provide details for all methods within an interface.

Pragmatically, the required details can be added in stages. If some, but not all, details are implemented in a class, it is said to be an abstract class.

The following steps illustrate the use of abstract classes in implementing an Interface. If desired, all details in one step, skipping steps 1 and 2 below.

  1. Abstract class GrinnellCSCourse.java provides a framework that will extend GrinnellCourse and implement CC2008, names of methods for paradigms and language support are given (as abstract methods), but no details are added to the CC2008 Interface.

  2. Abstract class GrinnellCSCourse1.java extends GrinnellCSCourse1.java, but it could extend GrinnellCourse and implement CC2008. GrinnellCSCourse identifies some methods (without details), but the method signatures are repeated when those methos are implemented.

  3. Class GrinnellCSCourse2.java extends GrinnellCSCourse2 and adds the remaining implementation details, so that this class can be used to create objects. (Since GrinnellCSCourse2 contains some implementation, GrinnellCSCourse3 cannot simply extend GrinnellCourse and implement CC2008 directly unless the details from GrinnellCSCourse2 are copied.)


This document is available on the World Wide Web as

http://www.walker.cs.grinnell.edu/courses/207.sp12/readings/reading-inheritance-generics.shtml

created 12 February 2012 by Henry M. Walker
last revised 13 February 2012
Valid HTML 4.01! Valid CSS!
For more information, please contact Henry M. Walker at walker@cs.grinnell.edu.


Copyright © 2011-2012 Henry M. Walker.
CC-BY-NC-SA
This work is licensed under a Creative Commons Attribution-Noncommercial-Share Alike 3.0 United States License .