C++:同名隐藏和赋值兼容规则

1、同名隐藏

同名隐藏,即在C++的继承中,只要子类的函数名和父类的函数名相同,子类中的函数将会隐藏全部父类中和子类的成员函数同名的函数ios

特别注意:函数

和函数之间的重载不一样,这里只要求函数的名字相同,而对函数的参数列表是否相同不作要求。话句话说父类中和子类的成员函数名相同但参数列表不一样的成员函数也会被隐藏spa

示例:指针

 1 #include<iostream>
 2 using namespace std;
 3 class Father{ //父类
 4 public:
 5     Father()=default;
 6     Father(int v):value(v){}
 7     void show(){
 8         cout<<"调用Father类中的成员函数show()"<<endl; 
 9     }
10     void show(int a){
11         cout<<"调用Father类中的成员函数show(int)"<<endl; 
12     }
13 private:
14     int value; 
15 }; 
16 
17 class Son:public Father{ //子类
18 public:
19     Son()=default;
20     Son(int v):value(v){}
21     void show(){  //对父类中的方法show()和方法show(int)进行了同名隐藏 22         cout<<"调用Son类中的成员函数show()"<<endl; 
23     }
24 private:
25     int value; 
26 };
27 
28 int main(){
29     Son s;
30     s.show();
31     //s.show(1); //错误:方法show(int)被同名隐藏了 32     s.Father::show(); //父类的方法show()和方法show(int)确实被子类Son继承了,但被子类Son中的同名方法show()给隐藏了,没法经过子类的对象显式的调用 33     s.Father::show(1);
34     return 0;
35 } 

 

2、赋值兼容规则

所谓赋值兼容规则,即在任何须要基类对象的地方均可以用该基类的公有派生类的对象来代替,它主要包括如下状况:code

• 派生类的对象能够赋值给基类的对象,此时的赋值操做主要是把派生类对象中所包含的对应基类的子对象赋值给基类对象对象

特别注意:blog

反过来(即将基类对象赋值给派生类对象)不行,由于派生类对象中的新成员将无值可赋继承

示意图:io

示例:class

 1 #include<iostream>
 2 using namespace std;
 3 class Father{ //父类
 4 public:
 5     Father()=default;
 6     Father(int value):father_value(value){}
 7     void show(){
 8         cout<<"Father类中的成员变量的值为:"<<father_value<<endl;
 9     }
10 private:
11     int father_value; 
12 };
13 
14 class Son:public Father{ //子类
15 public:
16     Son()=default;
17     Son(int value):Father(value),son_value(value){}
18     void show(){
19         cout<<"Son类中的成员变量的值为:"<<son_value<<endl;
20     }
21 private:
22     int son_value; 
23 };
24 
25 int main(){
26     Father father(10);
27     Son son(20);
28 father=son; //将派生类对象赋值给基类对象
29     father.show();
30     return 0; 
31 }

• 能够将一个派生类对象的地址赋值给其基类的指针变量

特别注意:

1.只能经过该指针访问派生类中由基类继承来的隐藏对象,不能访问派生类中的新成员

2.此操做的本质是将指针指向派生类中由基类继承来的隐藏对象

3.不能将一个基类对象的地址赋值给一个派生类的指针变量

示意图:

示例:

 1 #include<iostream>
 2 using namespace std;
 3 class Father{ //父类
 4 public:
 5     Father()=default;
 6     Father(int value):father_value(value){}
 7     void show(){
 8         cout<<"Father类中的成员变量的值为:"<<father_value<<endl;
 9     }
10 private:
11     int father_value; 
12 };
13 
14 class Son:public Father{ //子类
15 public:
16     Son()=default;
17     Son(int value):Father(value),son_value(value){}
18     void show(){
19         cout<<"Son类中的成员变量的值为:"<<son_value<<endl;
20     }
21     void new_func(){
22         cout<<"调用Son类中的成员方法:new_func()"<<endl;
23     }
24 private:
25     int son_value; 
26 };
27 
28 int main(){
29     Son son(20);
30 Father *ptr=&son;//将派生类对象的地址赋值给基类类型的指针 31 ptr->show(); 32 //ptr->new_func(); //错误:只能经过该指针访问派生类中由基类继承来的隐藏对象,不能访问派生类中的新成员
33     return 0; 
34 }

• 派生类对象能够初始化基类的引用

特别注意:

1.只能经过该引用访问派生类中由基类继承来的隐藏对象,不能访问派生类中的新成员

2.此操做的本质是为派生类中由基类继承来的隐藏对象起一个别名

3.不能用基类对象来初始化派生类的引用

示意图:

示例:

 1 #include<iostream>
 2 using namespace std;
 3 class Father{ //父类
 4 public:
 5     Father()=default;
 6     Father(int value):father_value(value){}
 7     void show(){
 8         cout<<"Father类中的成员变量的值为:"<<father_value<<endl;
 9     }
10 private:
11     int father_value; 
12 };
13 
14 class Son:public Father{ //子类
15 public:
16     Son()=default;
17     Son(int value):Father(value),son_value(value){}
18     void show(){
19         cout<<"Son类中的成员变量的值为:"<<son_value<<endl;
20     }
21     void new_func(){
22         cout<<"调用Son类中的成员方法:new_func()"<<endl;
23     }
24 private:
25     int son_value; 
26 };
27 
28 int main(){
29     Son son(20);
30 Father &father=son;//用派生类来初始化基类的引用 31 father.show(); 32 //father.new_func(); //错误:只能经过该引用访问派生类中由基类继承来的隐藏对象,不能访问派生类中的新成员
33     return 0; 
34 }

相关文章
相关标签/搜索