Q:类之间是否存在直接的关联关系?
由这个问题由此联想到生活中的例子:组合
A.组合关系:整体与部分的关系
组合关系的描述--代码示例
#include <iostream>
#include <string>
using namespace std;
class Memory
{
public:
Memory()
{
cout << "Memory()" << endl;
}
~Memory()
{
cout << "~Memory()" << endl;
}
};
class Disk
{
public:
Disk()
{
cout << "Disk()" << endl;
}
~Disk()
{
cout << "~Disk()" << endl;
}
};
class CPU
{
public:
CPU()
{
cout << "CPU()" << endl;
}
~CPU()
{
cout << "~CPU()" << endl;
}
};
class MainBoard
{
public:
MainBoard()
{
cout << "MainBoard()" << endl;
}
~MainBoard()
{
cout << "~MainBoard()" << endl;
}
};
class Computer
{
Memory mMem;
Disk mDisk;
CPU mCPU;
MainBoard mMainBoard;
public:
Computer()
{
cout << "Computer()" << endl;
}
void power()
{
cout << "power()" << endl;
}
void reset()
{
cout << "reset()" << endl;
}
~Computer()
{
cout << "~Computer()" << endl;
}
};
int main()
{
Computer c;
return 0;
}
从该段代码可以看出,电脑的每一个部分都是独立的,但是在创建电脑的类时对每个部分进行了调用,期待的输出是其它类的对象作为电脑类的成员使用
结果输出如下
组合关系的特点
1.将其它类的对象作为当前类的成员使用
2.当前类的对象与成员对象的生命周期相同
3.成员对象在用法上与普通对象完全一致
B.继承关系:父子关系
面向对象中的继承指类之间的父子关系
1.子类拥有父类的所有属性和行为
2.子类就是一种特殊的父类
3.子类对象可以当作父类对象使用
4.子类中可以添加父类没有的方法和属性
继承关系的代码描述
#include <iostream>
#include <string>
using namespace std;
class Memory
{
public:
Memory()
{
cout << "Memory()" << endl;
}
~Memory()
{
cout << "~Memory()" << endl;
}
};
class Disk
{
public:
Disk()
{
cout << "Disk()" << endl;
}
~Disk()
{
cout << "~Disk()" << endl;
}
};
class CPU
{
public:
CPU()
{
cout << "CPU()" << endl;
}
~CPU()
{
cout << "~CPU()" << endl;
}
};
class MainBoard
{
public:
MainBoard()
{
cout << "MainBoard()" << endl;
}
~MainBoard()
{
cout << "~MainBoard()" << endl;
}
};
class Computer
{
Memory mMem;
Disk mDisk;
CPU mCPU;
MainBoard mMainBoard;
public:
Computer()
{
cout << "Computer()" << endl;
}
void power()
{
cout << "power()" << endl;
}
void reset()
{
cout << "reset()" << endl;
}
~Computer()
{
cout << "~Computer()" << endl;
}
};
int main()
{
Computer c;
return 0;
}
运行结果
由运行的结果可以发现在子类中没有定义 成员函数void method(),但是输出的结果中却有mv的值,这是因为继承关系的优点--子类拥有父类的所有属性和行为
同时须知道--子类就是一个特殊的父类,子类对象可以直接初始化父类对象,子类对象可以直接赋值给父类对象
继承的意义--继承是C++中代码复用的重要手段。通过继承,可以获得父类的所有功能,并且可以在子类中重写已有功能,或者添加新功能
Q:子类是否可以直接访问父类的私有成员?
代码验证
#include <iostream>
#include <string>
using namespace std;
class Parent
{
private:
int mv;
public:
Parent()
{
mv = 100;
}
int value()
{
return mv;
}
};
class Child : public Parent
{
public:
int addValue(int v)
{
mv = mv + v;
}
};
int main()
{
return 0;
}
根据上面的继承关系--子类拥有父类的所有属性和行为,我们可以期待在子类的 int addValue(int v)的成员函数中对父类的私有成员变量mv进行改动
运行结果
从运行的结果我们可以得知,子类的int addValue(int v)成员函数出错,提示mv是父类私有成员变量,不能对其进行访问,这与我们期待的结果不一样,所以在子类对父类的修饰的私有成员进行访问有了一种新的访问级别--protected
继承中的访问级别
1.面向对象中的访问级别不只是public和private
2.可以定义protected访问级别
3.关键字protected的意义--修饰的成员不能被外界直接访问,修饰的成员可以被子类直接访问
代码示例--protected的运用
#include <iostream>
#include <string>
using namespace std;
class Parent
{
protected:
int mv;
public:
Parent()
{
mv = 100;
}
int value()
{
return mv;
}
};
class Child : public Parent
{
public:
int addValue(int v)
{
mv = mv + v;
}
};
int main()
{
Parent p;
cout << "p.mv = " << p.value() << endl;
// p.mv = 1000; // error
Child c;
cout << "c.mv = " << c.value() << endl;
c.addValue(50);
cout << "c.mv = " << c.value() << endl;
// c.mv = 10000; // error
return 0;
}
运行结果
但是当我们在int main中对mv进行修改时得到的运行结果
可以看到在子类的外部不允许对父类的私有成员变量进行修改
由以上的两个实例我们可以一张图片来完全表示继承关系
小结
1.面向对象的访问级不只是public和private
2.protected修饰的成员不能被外界所访问
3.protected使得子类能够访问父类的成员
4.protected关键字是为了继承而专门设计的
5.没有protected就无法完成真正意义上的代码复用
三.C++中支持三种不同的继承方式
1.public继承--父类成员在子类中保持原有访问级别
2.private继承--父类成员在子类中变私有成员
3.protected继承--父类中的公有成员变为保护成员,其它成员保持不变
免责声明:本站发布的内容(图片、视频和文字)以原创、转载和分享为主,文章观点不代表本网站立场,如果涉及侵权请联系站长邮箱:is@yisu.com进行举报,并提供相关证据,一经查实,将立刻删除涉嫌侵权内容。