在设计时,常常希望基类仅仅作为其派生类的一个接口
当继承一个抽象类时,必须实现所有的纯虚函数,否则继承出的类也将是
一个抽象类
基类Instrument中的函数总是 哑 函数。
建立公共接口的唯一原因是它能对于每个不同的子类有不同的表示
使用了纯虚函数。因为类中全是纯虚函数,所以我们称之为纯抽象类
//: C15:Instrument5.cpp
// From Thinking in C++, 2nd Edition
// Available at http://www.BruceEckel.com
// (c) Bruce Eckel 2000
// Copyright notice in Copyright.txt
// Pure abstract base classes
#include <iostream>
using namespace std;
enum note { middleC, Csharp, Cflat }; // Etc.
class Instrument {
public:
// Pure virtual functions:
virtual void play(note) const = 0;
virtual char* what() const = 0;
// Assume this will modify the object:
virtual void adjust(int) = 0;
};
// Rest of the file is the same ...
class Wind : public Instrument {
public:
void play(note) const {
cout << "Wind::play" << endl;
}
char* what() const { return "Wind"; }
void adjust(int) {}
};
class Percussion : public Instrument {
public:
void play(note) const {
cout << "Percussion::play" << endl;
}
char* what() const { return "Percussion"; }
void adjust(int) {}
};
class Stringed : public Instrument {
public:
void play(note) const {
cout << "Stringed::play" << endl;
}
char* what() const { return "Stringed"; }
void adjust(int) {}
};
class Brass : public Wind {
public:
void play(note) const {
cout << "Brass::play" << endl;
}
char* what() const { return "Brass"; }
};
class Woodwind : public Wind {
public:
void play(note) const {
cout << "Woodwind::play" << endl;
}
char* what() const { return "Woodwind"; }
};
// Identical function from before:
void tune(Instrument& i) {
// ...
i.play(middleC);
}
// New function:
void f(Instrument& i) { i.adjust(1); }
int main() {
Wind flute;
Percussion drum;
Stringed violin;
Brass flugelhorn;
Woodwind recorder;
tune(flute);
tune(drum);
tune(violin);
tune(flugelhorn);
tune(recorder);
f(flugelhorn);
getchar();
} ///:~
纯虚函数是非常有用的,因为它们使得类有明显的抽象性,并告诉用户和
编译器打算如何使用
纯虚函数禁止对抽象类的函数以传值方式调用。这也是防止对象切片的一种
方法
纯虚函数防止产生完全的VTABLE,但这并不意味着我们不希望对其他一些函数
产生函数体
输出
Wind::play
Percussion::play
Stringed::play
Brass::play
Woodwind::play