类与继承总结

一、类之间的关系
在面向对象技术中,类是数据和操作的集合,他们之间有三种主要关系:has-a,uses-a和is-a。
has-a表示类的包含关系,用于描述一个类由多个“部件类”构成。C++实现has-a的关系用类成员表示,即一个类中的数据成员是另一种已经定义的类。
uses-a表示一个类部分地使用另一个类。在面向对象的技术中,这种关系通过类之间成员函数的相互关系,定义友元或对象参数传递来实现。
is-a表示一种分类方式,描述类的抽象和层次关系。is-a关系具有传递性,但不具有对称性。is-a机制称为“继承”。

二、继承的定义
在原有类的基础上生成(派生)新类的方式就是继承。由多个类派生一个新的类的方法,称为“多继承”。

三、描述类继承的语句格式
class 派生类名:基类名表
{
数据成员和成员函数说明
};
其中,“基类名表的”语句格式为:
访问控制 基类名1,访问控制 基类名2,…,访问控制 基类名n
用于表示当前定义的派生类的各个基类。

“访问控制”是表示继承权限的关键字,称为访问描述符。可以是:
public 公有继承
private 私有继承
protected 保护继承
如果省略访问描述符,则C++认为是私有继承。如果用关键字struct(而不是class)定义类,则省略访问描述符时认为是公有继承。

四、访问控制
公有继承:基类中所有的public成员称为派生类中的public成员,基类中所有protected成员成为派生类中的protected成员。
私有继承:基类中所有的public成员和protected成员同时称为派生类中的private成员。
保护继承:基类中所有的public成员和protected成员同时称为派生类中的protected成员。
不论派生类以何种方式继承基类,都不能直接使用基类的private成员。
注:基类的私有成员在派生类中不可见,但并不是说在建立派生类对象时,就不创建从基类继承的私有数据成员。

五、访问声明
定义:C++提供一种访问调节机制,使一些本来在派生类中不可见的成员变为可访问的,称为访问声明。
语句格式:
基类名::成员

注意事项:
1)访问声明仅调整名字的访问权限
当被声明对象是数据成员时,不可说明为任何类型;当被声明对象为成员函数时,只能是函数名本身,不能带参数和返回类型说明。例如:

class B
{ public:
        int c;
        void get_XY()
        { /*...*/
        }
 };
 class D:private B
 {      int d;
        public:
        int B::c;//错误,带类型
        B::get_XY;//正确
  };

2)访问声明不允许在派生类中降低或提升基类成员的可访问性
例如:

class B
{ public: int a;
private: int b;
protected: int c;
};
class D:private B
{
public:
B::a;//正确
B::b;//错误,私有成员不能用于访问声明
protected:
B::c;//正确
B::a;//错误,不能降低基类成员的可访问性
};

3)对重载函数名的访问声明将调整基类所有同名函数的访问域
1、调整同名的重载函数

class X
{ public:
f();
f(int);
};
class Y:private X
{ public:
        X::f;//使X::f和X::f(int)在Y中都为公有的
 };

2、不同访问域的重载函数名不能用于访问声明

class X
{ private:
        f(int);
  public:
        f();
 };
 class Y:private X
 { public:
       X::f;//错误,访问声明具有二义性,不能调整其访问性
 };

3、派生类中与基类名字相同的成员不可调整访问权限

class X
{ public:
       f();
 };
 class Y:private X
 { public:
      void f(int);
      X::f;//错误,f有两次说明,不能调整期访问权限
  };

六、重名成员
C++允许派生类的成员与基类成员重名。在派生类中访问访问重名成员时,屏蔽基类的同名成员。如果要在派生类中使用基类的同名成员,可以显示地使用作用域指定,格式为:
类名::成员

1、重名数据成员
如果在派生类中定义了与基类相同名字的数据成员,根据继承规则,在建立派生类对象时,系统会分别建立不同的存储空间。

#include<iostream>
using namespace std;
class Base
{ public:
int a,b;
void print()
{ cout<<a<<b<<endl;}
};
class Derived:public Base3
{
public:
int b,c;
void print()
{ cout<<c<<endl;}
};
int main()
{ Derived d;
   d.a=1;
   d.Base::b=2;//Base::b使用的是Base类的数据成员b
   d.b=3;//这里使用的是Derived类的数据成员b
   d.Base::print();//这里使用的是Base的成员函数
  /*...*/
  }

2、在派生类中定义与基类同名的成员函数,称为在派生类中重载基类的成员函数。由调用形式指示this指针的不同类型,调用不同版本的成员函数。
例子如上

七、重载成员函数
定义:派生类中定义与基类同名的成员函数

八:基类的初始化
通过派生类的构造函数使用冒号语法的参数初始式实现这种功能
语法格式:
构造函数名(变元表):基类(变元表),数据成员1(变元表),…,数据成员n(变元表)
{ // }

冒号后面是基类构造函数及对象成员各自对应的参数初始式。
构造函数执行顺序:首先执行基类,然后执行类对象成员,最后执行派生类本身。

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值