Student
Class DesignAt this point, the design plan for the Student
class is to use a string
object to represent the name and a valarray<double>
object to represent the quiz scores. How should this be done? You might be tempted to publicly derive a Student
class from these two classes. That would be an example of multiple public inheritance, which C++ allows, but it would be inappropriate here. The reason is that the relationship of a student to these classes doesn’t fit the is-a model. A student is not a name. A student is not an array of quiz scores. What you have here is a has-a relationship. A student has a name, and a student has an array of quiz scores. The usual C++ technique for modeling has-a relationships is to use composition or containment—that is, to create a class composed of, or containing, members that are objects of another class. For example, you can begin a Student
class declaration like this:
class Student
{
private:
string name; // use a string object for name
valarray<double> scores; // use a valarray<double> object for scores
...
};
As usual, the class makes the data members private. This implies that the Student
class member functions can use the public interfaces of the string
and valarray<double>
classes to access and modify the name
and scores
objects, but the outside world cannot do so. The only access the outside world will have to name
and scores
is through the public interface defined for the Student
class (see Figure 14.1). A common way of describing this is to say that the Student
class acquires the implementation of its member objects but doesn’t inherit the interface. For example, a Student
object uses the string
implementation rather than a char * name
or a char name[26]
implementation for holding the name. But a Student
object does not innately have the ability to use the string operator+=()
function for appending.
The fact that a class object doesn’t automatically acquire the interface of a contained object is a good thing for a has-a relationship. For example, string
overloads the +
operator to allow concatenating two strings, but, conceptually, it doesn’t make sense to concatenate two Student
objects. That’s one reason not to use public inheritance in this case. On the other hand, parts of the interface for the contained class may make sense for the new class. For example, you might want to use the operator<()
method from the string
interface to sort Student
objects by name. You can do so by defining a Student::operator<()
member function that internally uses the string::operator<()
function. Let’s move on to some details.
3.138.35.193