在C++中,继承是一种面向对象编程的核心概念之一。继承可以使得一个类(子类)可以从另一个类(父类)继承属性和方法。在C++中,有三种不同的继承方式:public
继承、protected
继承和private
继承。每种继承方式都有其自身的意义和使用场景。
public继承
public
继承是最常见的一种继承方式,也是默认的继承方式。在public
继承中,子类可以访问父类的public
成员,但是不能访问父类的private
成员。public继承的意义在于,可以使得子类继承父类的接口(public
成员),从而使得子类可以更方便地使用父类的方法和属性。
protected继承
protected
继承是一种介于public
继承和private
继承之间的继承方式。在protected
继承中,子类可以访问父类的protected
成员和public
成员,但是不能访问父类的private
成员。protected
继承的意义在于,可以使得子类能够访问父类的protected
成员,从而使得子类可以重用父类的实现,而不用对外暴露父类的实现细节。
private继承
private
继承是一种最严格的继承方式。在private
继承中,子类可以访问父类的protected
和public
成员,但是不能访问父类的private
成员。private
继承的意义在于,可以使得子类不能直接使用父类的接口,而是需要通过自己的方法来实现。这种方式一般用于实现细节隐藏,即不希望子类能够访问父类的实现细节。
C++中的继承方式设计是为了实现代码的重用和继承,同时也可以实现对代码实现细节的隐藏和保护。不同的继承方式可以在不同的场景下发挥作用。
假设我们有一个动物类 Animal
,以及三个派生类 Dog
、Cat
和 Bird
,分别继承自 Animal
。下面给出使用不同继承方式的代码示例:
public 继承
class Animal {
public:
void eat() {
cout << "Animal is eating" << endl;
}
};
class Dog : public Animal {
public:
void bark() {
cout << "Dog is barking" << endl;
}
};
class Cat : public Animal {
public:
void meow() {
cout << "Cat is meowing" << endl;
}
};
class Bird : public Animal {
public:
void fly() {
cout << "Bird is flying" << endl;
}
};
这里的 Dog
、Cat
和 Bird
都是以 public
方式继承 Animal
类。这意味着它们可以访问 Animal
类中的公共成员(如 eat()
函数),并将其作为自己的公共成员。
protected 继承
class Animal {
protected:
void eat() {
cout << "Animal is eating" << endl;
}
};
class Dog : protected Animal {
public:
void bark() {
cout << "Dog is barking" << endl;
eat();
}
};
class Cat : protected Animal {
public:
void meow() {
cout << "Cat is meowing" << endl;
eat();
}
};
class Bird : protected Animal {
public:
void fly() {
cout << "Bird is flying" << endl;
eat();
}
};
这里的 Dog
、Cat
和 Bird
都是以 protected
方式继承 Animal
类。这意味着它们可以访问 Animal
类中的保护成员(如 eat()
函数),并将其作为自己的保护成员。由于 eat()
函数是保护成员,因此在 Dog
、Cat
和 Bird
中都可以直接访问它。
private 继承
class Animal {
private:
void eat() {
cout << "Animal is eating" << endl;
}
};
class Dog : private Animal {
public:
void bark() {
cout << "Dog is barking" << endl;
eat();
}
};
class Cat : private Animal {
public:
void meow() {
cout << "Cat is meowing" << endl;
eat();
}
};
class Bird : private Animal {
public:
void fly() {
cout << "Bird is flying" << endl;
eat();
}
};
这里的 Dog
、Cat
和 Bird
都是以 private
方式继承 Animal
类。这意味着它们无法访问 Animal
类中的公共或保护成员,而只能将其作为自己的私有成员。由于 eat()
函数是私有成员,因此在 Dog
、Cat
和 Bird
中都无法直接访问它,只能通过 Animal
中公开的接口(如 eat()
函数的调用)来访问它。
为了能够解释得更加清楚,比如如下例子:
假设我们正在编写一个游戏,这个游戏有多个角色,每个角色都有自己的属性(如血量、攻击力等)和行为(如移动、攻击等),并且角色之间有不同的关系(如团队关系、敌对关系等)。我们使用C++来实现这个游戏。
首先,我们需要一个基类来表示所有角色的共同属性和行为。我们可以定义一个叫做“Character
”的类,其中包含角色的基本属性和行为,如下所示:
class Character {
protected:
int health;
int attackPower;
public:
virtual void move(int x, int y) = 0;
virtual void attack(Character& target) = 0;
};
在这个类中,我们使用了protected
访问修饰符,这意味着子类可以访问这些属性和方法,但其他类不能访问它们。同时,我们还使用了纯虚函数,这是一种只声明而不实现的函数,它告诉编译器这些函数需要在子类中被重写。
接下来,我们可以定义一些子类来表示不同类型的角色。例如,我们可以定义一个“Warrior
”类,表示一名战士,如下所示:
class Warrior : public Character {
public:
Warrior() {
health = 100;
attackPower = 10;
}
void move(int x, int y) override {
// 移动逻辑
}
void attack(Character& target) override {
// 攻击逻辑
}
};
在这个类中,我们使用了public
继承,这意味着子类继承了父类的所有属性和方法,并且这些属性和方法都是public
的,可以被其他类访问。同时,我们重写了基类中的纯虚函数,实现了战士的具体行为。
除了战士,我们还可以定义其他类型的角色,如法师、弓箭手等等。这些角色都继承自基类“Character
”,并且根据不同的需求,可以使用不同的继承方式。
例如,我们可以定义一个“Wizard
”类,表示一名法师,如下所示:
class Wizard : protected Character {
public:
Wizard() {
health = 50;
attackPower = 20;
}
void move(int x, int y) override {
// 移动逻辑
}
void attack(Character& target) override {
// 攻击逻辑
}
};
在这个类中,我们使用了protected
继承,这意味着子类继承了父类的所有属性和方法,但这些属性和方法都是protected
的,不能被其他类访问。
private
继承大家可以根据上述讲解自行实现,动手操作一下,有助于自己理解。