C++ 继承机制详解
编程小白也能理解的继承知识点汇总
用大白话解释面向对象编程的核心概念
什么是继承?
继承就像家族遗传。想象一下:
你从父母那里继承了某些特征 – 比如眼睛颜色、身高、发色等。在编程中,继承就是让一个类(子类)获得另一个类(父类)的属性和方法。
在C++中,继承允许我们基于已有的类创建新类。这样做的好处是:
- ✅ 代码重用:不需要重复编写相同的代码
- ✅ 层次结构:可以创建有逻辑关系的类结构
- ✅ 多态性:为面向对象编程的另一个重要特性打下基础
父类:动物
- 属性:年龄、体重
- 方法:吃()、睡()
↓
子类:狗
- 继承:年龄、体重
- 继承:吃()、睡()
- 新增:叫()
子类:猫
- 继承:年龄、体重
- 继承:吃()、睡()
- 新增:抓()
继承的基本语法
在C++中,使用冒号:表示继承关系:
class Parent { // 父类(基类)
public:
void parentMethod() {
cout << “父类方法” << endl;
}
};
class Child : public Parent { // 子类(派生类)
public:
void childMethod() {
cout << “子类方法” << endl;
}
};
public:
void parentMethod() {
cout << “父类方法” << endl;
}
};
class Child : public Parent { // 子类(派生类)
public:
void childMethod() {
cout << “子类方法” << endl;
}
};
这样,Child类就自动拥有了Parent类的parentMethod()方法:
Child childObj;
childObj.parentMethod(); // 调用继承的方法
childObj.childMethod(); // 调用自己的方法
childObj.parentMethod(); // 调用继承的方法
childObj.childMethod(); // 调用自己的方法
三种继承方式
C++中有三种继承方式,决定了基类成员在派生类中的访问权限:
继承方式 | 基类的public成员 | 基类的protected成员 | 基类的private成员 |
---|---|---|---|
public继承 | 在派生类中为public成员 | 在派生类中为protected成员 | 在派生类中不可访问 |
protected继承 | 在派生类中为protected成员 | 在派生类中为protected成员 | 在派生类中不可访问 |
private继承 | 在派生类中为private成员 | 在派生类中为private成员 | 在派生类中不可访问 |
编程小白建议: 大多数情况下使用public继承,因为它最符合”是一个”的关系(如:狗是一种动物)。
函数重写(覆盖)
子类可以修改继承自父类的方法,这叫做函数重写或覆盖。
class Animal {
public:
void makeSound() {
cout << “动物发出声音” << endl;
}
};
class Dog : public Animal {
public:
void makeSound() { // 重写父类方法
cout << “汪汪汪!” << endl;
}
};
Dog myDog;
myDog.makeSound(); // 输出”汪汪汪!”而不是”动物发出声音”
public:
void makeSound() {
cout << “动物发出声音” << endl;
}
};
class Dog : public Animal {
public:
void makeSound() { // 重写父类方法
cout << “汪汪汪!” << endl;
}
};
Dog myDog;
myDog.makeSound(); // 输出”汪汪汪!”而不是”动物发出声音”
注意: 重写不同于重载!重写是子类重新定义父类的方法,而重载是在同一个类中有多个同名但参数不同的方法。
构造函数与析构函数
在继承体系中,对象的创建和销毁遵循特定顺序:
构造顺序:
- 1. 基类的构造函数
- 2. 成员对象的构造函数(如果有)
- 3. 派生类自己的构造函数
析构顺序:
- 1. 派生类自己的析构函数
- 2. 成员对象的析构函数
- 3. 基类的析构函数
class Base {
public:
Base() { cout << “基类构造” << endl; }
~Base() { cout << “基类析构” << endl; }
};
class Derived : public Base {
public:
Derived() { cout << “派生类构造” << endl; }
~Derived() { cout << “派生类析构” << endl; }
};
int main() {
Derived d; // 输出:基类构造 -> 派生类构造
return 0;
} // 输出:派生类析构 -> 基类析构
public:
Base() { cout << “基类构造” << endl; }
~Base() { cout << “基类析构” << endl; }
};
class Derived : public Base {
public:
Derived() { cout << “派生类构造” << endl; }
~Derived() { cout << “派生类析构” << endl; }
};
int main() {
Derived d; // 输出:基类构造 -> 派生类构造
return 0;
} // 输出:派生类析构 -> 基类析构
多继承
C++允许一个类同时继承多个父类,这就是多继承:
class Father {
public:
void fatherMethod() { … }
};
class Mother {
public:
void motherMethod() { … }
};
class Child : public Father, public Mother {
// 同时拥有Father和Mother的方法
};
Child c;
c.fatherMethod(); // 正确
c.motherMethod(); // 正确
public:
void fatherMethod() { … }
};
class Mother {
public:
void motherMethod() { … }
};
class Child : public Father, public Mother {
// 同时拥有Father和Mother的方法
};
Child c;
c.fatherMethod(); // 正确
c.motherMethod(); // 正确
注意: 多继承可能带来”菱形继承”问题(一个类通过不同路径继承同一个基类两次)。解决方法是使用虚继承:
class Child : virtual public Parent { … }
继承中的访问控制
理解三个访问修饰符在继承中的作用:
- public:类内外都可以访问
- protected:类内和子类中可以访问
- private:只有类内可以访问
class Base {
public:
int publicVar;
protected:
int protectedVar;
private:
int privateVar;
};
class Derived : public Base {
public:
void test() {
publicVar = 1; // 正确
protectedVar = 2; // 正确
privateVar = 3; // 错误!不能访问基类私有成员
}
};
public:
int publicVar;
protected:
int protectedVar;
private:
int privateVar;
};
class Derived : public Base {
public:
void test() {
publicVar = 1; // 正确
protectedVar = 2; // 正确
privateVar = 3; // 错误!不能访问基类私有成员
}
};