#include <iostream>
#include <string>
using namespace std;
/*
* 基类1 - 动物类
* 包含纯虚函数,是抽象类
*/
class Animal {
protected:
string name;
int age;
public:
/* 构造函数 */
Animal(const string& name, int age) : name(name), age(age) {
cout << "Animal构造函数被调用" << endl;
}
/* 虚函数 - 可以被派生类覆盖 */
virtual void makeSound() const {
cout << "动物发出声音" << endl;
}
/* 纯虚函数 - 使类成为抽象类,派生类必须实现 */
virtual void eat() const = 0;
/* 非虚函数 - 不建议在派生类中覆盖 */
void sleep() const {
cout << name << "正在睡觉" << endl;
}
/* 虚析构函数 - 确保派生类对象被正确销毁 */
virtual ~Animal() {
cout << "Animal析构函数被调用" << endl;
}
};
/*
* 基类2 - 可飞行接口
* 纯抽象类
*/
class Flyable {
public:
virtual void fly() const = 0;
virtual ~Flyable() = default;
};
/*
* 基类3 - 可游泳接口
* 包含默认实现的虚函数
*/
class Swimmable {
public:
virtual void swim() const {
cout << "在水中游泳" << endl;
}
virtual ~Swimmable() = default;
};
/*
* 派生类1 - 公有继承
* Dog 公有继承自 Animal
*/
class Dog : public Animal {
private:
string breed;
public:
/* 构造函数 */
Dog(const string& name, int age, const string& breed)
: Animal(name, age), breed(breed) {
cout << "Dog构造函数被调用" << endl;
}
/* 覆盖基类的虚函数 */
void makeSound() const override {
cout << name << "汪汪叫" << endl;
}
/* 实现基类的纯虚函数 */
void eat() const override {
cout << name << "正在吃狗粮" << endl;
}
/* 派生类特有的方法 */
void fetch() const {
cout << name << "正在接飞盘" << endl;
}
/* 析构函数 */
~Dog() override {
cout << "Dog析构函数被调用" << endl;
}
};
/*
* 派生类2 - 多重继承
* Duck 同时继承自 Animal, Flyable 和 Swimmable
*/
class Duck : public Animal, public Flyable, public Swimmable {
public:
/* 构造函数 */
Duck(const string& name, int age) : Animal(name, age) {
cout << "Duck构造函数被调用" << endl;
}
/* 覆盖Animal的虚函数 */
void makeSound() const override {
cout << name << "嘎嘎叫" << endl;
}
/* 实现Animal的纯虚函数 */
void eat() const override {
cout << name << "正在吃小鱼和谷物" << endl;
}
/* 实现Flyable的纯虚函数 */
void fly() const override {
cout << name << "正在飞翔" << endl;
}
/* 覆盖Swimmable的虚函数 */
void swim() const override {
cout << name << "正在水上游泳" << endl;
}
/* 析构函数 */
~Duck() override {
cout << "Duck析构函数被调用" << endl;
}
};
/*
* 派生类3 - 保护继承
* ProtectedDerived 保护继承自 Animal
*/
class ProtectedDerived : protected Animal {
public:
/* 构造函数 */
ProtectedDerived(const string& name, int age) : Animal(name, age) {}
/*
* 保护继承后,基类的公有成员在派生类中变为保护成员
* 可以通过派生类的公有方法间接访问
*/
void showInfo() const {
cout << "保护继承示例: " << name << ", " << age << "岁" << endl;
makeSound(); /* 可以访问基类的protected成员 */
}
/* 实现基类的纯虚函数 */
void eat() const override {
cout << "保护继承的eat实现" << endl;
}
};
/*
* 派生类4 - 私有继承
* PrivateDerived 私有继承自 Animal
*/
class PrivateDerived : private Animal {
public:
/* 构造函数 */
PrivateDerived(const string& name, int age) : Animal(name, age) {}
/*
* 私有继承后,基类的公有和保护成员在派生类中变为私有成员
* 可以通过派生类的公有方法间接访问
*/
void showInfo() const {
cout << "私有继承示例: " << name << ", " << age << "岁" << endl;
makeSound(); /* 可以访问基类的protected成员(现在是private) */
}
/* 实现基类的纯虚函数 */
void eat() const override {
cout << "私有继承的eat实现" << endl;
}
};
/*
* 虚继承示例 - 解决菱形继承问题
* Base 作为虚基类
*/
class Base {
public:
int data;
Base(int val) : data(val) {}
virtual ~Base() = default;
};
/* Derived1 虚继承自 Base */
class Derived1 : virtual public Base {
public:
Derived1(int val) : Base(val) {}
};
/* Derived2 虚继承自 Base */
class Derived2 : virtual public Base {
public:
Derived2(int val) : Base(val) {}
};
/* FinalDerived 继承自 Derived1 和 Derived2 */
class FinalDerived : public Derived1, public Derived2 {
public:
/* 虚基类由最终派生类初始化 */
FinalDerived(int val1, int val2) : Base(val1), Derived1(val1), Derived2(val2) {}
};
int main() {
/* 1. 公有继承示例 */
cout << "===== 公有继承示例 =====" << endl;
Dog myDog("Buddy", 3, "Golden Retriever");
myDog.makeSound(); /* 调用派生类覆盖的方法 */
myDog.eat(); /* 调用派生类实现的纯虚函数 */
myDog.sleep(); /* 调用继承的基类方法 */
myDog.fetch(); /* 调用派生类特有的方法 */
/* 通过基类指针访问 */
Animal* animalPtr = &myDog;
animalPtr->makeSound(); /* 多态行为,调用Dog的实现 */
/* 2. 多重继承示例 */
cout << "\n===== 多重继承示例 =====" << endl;
Duck myDuck("Donald", 2);
myDuck.makeSound(); /* Animal的方法 */
myDuck.fly(); /* Flyable的方法 */
myDuck.swim(); /* Swimmable的方法 */
/* 通过不同基类指针访问 */
Flyable* flyPtr = &myDuck;
flyPtr->fly();
Swimmable* swimPtr = &myDuck;
swimPtr->swim();
/* 3. 保护继承示例 */
cout << "\n===== 保护继承示例 =====" << endl;
ProtectedDerived pd("Protected", 5);
pd.showInfo();
/* pd.makeSound(); // 错误: makeSound在ProtectedDerived中是protected的 */
/* 4. 私有继承示例 */
cout << "\n===== 私有继承示例 =====" << endl;
PrivateDerived prd("Private", 7);
prd.showInfo();
/* prd.makeSound(); // 错误: makeSound在PrivateDerived中是private的 */
/* 5. 虚继承示例 */
cout << "\n===== 虚继承示例 =====" << endl;
FinalDerived fd(10, 20);
/* 没有虚继承时,这里会有二义性 */
cout << "data = " << fd.data << endl; /* 输出10,因为由FinalDerived初始化 */
/* 6. 对象销毁顺序 */
cout << "\n===== 对象销毁顺序 =====" << endl;
/* 观察对象销毁时的析构函数调用顺序 */
/* 析构顺序与构造顺序相反,先派生后基类 */
return 0;
}
编译:g++ main.cpp -std=c++11
输出如下:
===== 公有继承示例 =====
Animal构造函数被调用
Dog构造函数被调用
Buddy汪汪叫
Buddy正在吃狗粮
Buddy正在睡觉
Buddy正在接飞盘
Buddy汪汪叫
===== 多重继承示例 =====
Animal构造函数被调用
Duck构造函数被调用
Donald嘎嘎叫
Donald正在飞翔
Donald正在水上游泳
Donald正在飞翔
Donald正在水上游泳
===== 保护继承示例 =====
Animal构造函数被调用
保护继承示例: Protected, 5岁
动物发出声音
===== 私有继承示例 =====
Animal构造函数被调用
私有继承示例: Private, 7岁
动物发出声音
===== 虚继承示例 =====
data = 10
===== 对象销毁顺序 =====
Animal析构函数被调用
Animal析构函数被调用
Duck析构函数被调用
Animal析构函数被调用
Dog析构函数被调用
Animal析构函数被调用
成功女性
鬼屋直播
内特巴加兹的纳什维尔圣诞节
提着心吊着胆
警魂
不再欺骗
怒火追击
人蛇大战李劲峰
我和我的第二故乡
打倒他们
喋血双雄粤配
圣诞计划
瞒天过海
设局
记忆奇旅
谍影重重4
好莱坞圣诞
寄了一整个春天
云
带着宠物躲战乱
阿尔格拉菲
卡萨托里亚
简单事情
布塔达姆巴斯卡纳拉亚纳
金鱼
一代爱国高僧圆瑛
除恶飞车党
妈妈别走
隔墙有情人
古董计中计之龙璧之战
门
莱拉
过细
步枪俱乐部
演员
绝境
黑猫
环游地球八十天
太空小子杰特之太空营地
梦之婚礼
倚天屠龙记之九阳神功
马1956
突破者
梁祝
美洲大陆
太空神鹰
雪豹之虎啸军魂
王者归来
新龙门客栈
演员
星际旅行10复仇女神
总是有爱在隔离粤配
火线追凶之冲破黑幕
怪物大乱捣
不再欺骗
方世玉粤配
船
绝地重生
引爆者
女心理师之心迷水影
油鬼子
破地狱
尸检6死者的秘密
暴走财神6
新流氓医生
穷养攻略
多想和你再见一面
银魂剧场新译红樱篇
环游地球八十天
不良影响小网红大黑幕
月球时代白日梦
小教父
暴裂无声
3年8班
橡皮头
降妖功德簿
哭泣的女人
血十三
悟空传
少女不毕业
美人鱼
3年8班
战锋对决
唤醒
贝茨先生与邮局真实的故事
钻石照耀钟鼓楼
小教父
3年8班
记忆大师
南少林之怒目金刚
狙击精英背水一战
大盘鸡
舞台姊妹1964
狄亚伯洛大决斗
到货即损doa
世界将不同
我的西门小故事
狼人杀启源
热搜
恶行之外
神秘教父
飞狐外传
驱魔天师
这是汤姆格林的纪录片
四大才子番外之真假唐伯虎
007之杀人执照
第一类型危险
婴儿车攻略
小情书
除匪
这个杀手不太冷静