淺析C++中的重載,隱藏和覆蓋
重載關(guān)系
一組函數(shù)要重載,必須處在同一個(gè)作用域中 ,而且函數(shù)名字相同,參數(shù)列表不同
代碼1中的Base中的 show() 和show(int) 屬于重載
代碼2中的Base中的 show() 和Derive中的show()不屬于重載不在同一個(gè)作用域下面
隱藏的關(guān)系(主要是指作用域隱藏)
在繼承結(jié)構(gòu)當(dāng)中,派生類(lèi)的同名成員,把基類(lèi)的同名成員給隱藏掉了
例如代碼2中的 Derive中的show() 和Base()中的show() ,show(int) 是隱藏關(guān)系
代碼1
class Base
{
public:
Base(int data=10):ma(data){
cout<<"Base"<<endl;
}
void show(){cout<<"Base Show()"<<endl;}
void show(int){cout<<"Base Show(int)"<<endl;}
~Base(){cout<<"~Base()"<<endl;}
protected:
int ma;
};
class Derive : public Base
{
public:
Derive(int data=20):Base(data),mb(data){
cout<<"Derive"<<endl;
}
~Derive(){cout<<"~Derive()"<<endl;}
private:
int mb;
};
int main(){
Derive d(20);
d.show(); //正常調(diào)用基類(lèi)show()
d.show(100); //正常調(diào)用基類(lèi)show(int)
return 0;
}
代碼2
class Base
{
public:
Base(int data=10):ma(data){
cout<<"Base"<<endl;
}
void show(){cout<<"Base Show()"<<endl;}
void show(int){cout<<"Base Show(int)"<<endl;}
~Base(){cout<<"~Base()"<<endl;}
protected:
int ma;
};
class Derive : public Base
{
public:
Derive(int data=20):Base(data),mb(data){
cout<<"Derive"<<endl;
}
void show(){cout<<"Derive Show()"<<endl;}
~Derive(){cout<<"~Derive()"<<endl;}
private:
int mb;
};
int main(){
Derive d(20);
d.show(); //調(diào)用子類(lèi)show()
d.show(100);//調(diào)用報(bào)錯(cuò) 報(bào)錯(cuò)信息 "Derive::show()函數(shù)不接受1個(gè)參數(shù)"
// 即 Derive中的show()方法把Base中的show()和show(int)都給隱藏掉了
// 所以d.show()沒(méi)問(wèn)題,調(diào)用的是派生類(lèi)的show(),但是d.show(100)報(bào)錯(cuò)了,因?yàn)?
// 父類(lèi)的show()和show(int)都被隱藏了,而派生類(lèi)Derive中沒(méi)有 show(int)方法所以報(bào)錯(cuò)了
// 如果想調(diào)用父類(lèi)的show(int) 要這樣寫(xiě) d.Base.show(100);
return 0;
}
基類(lèi)對(duì)象 -> 派生類(lèi)對(duì)象
類(lèi)型由上向下轉(zhuǎn) NOT OK
Base b(10);
Derive d(20);
d=b;// NOT OK
派生類(lèi)對(duì)象 ->基類(lèi)對(duì)象
類(lèi)型由下向上轉(zhuǎn) OK
Base b(10);
Derive d(20);
b=d;//OK

派生類(lèi)指針(引用) ->基類(lèi)指針 類(lèi)型由下向上轉(zhuǎn) OK
Base b(10);
Derive d(20);
Base *pb =&d;// OK 如下圖, 基類(lèi)指針只能訪(fǎng)問(wèn)到基類(lèi)那一部分的成員,所以是安全的

代碼3
class Base
{
public:
Base(int data=10):ma(data){
cout<<"Base"<<endl;
}
void show(){cout<<"Base Show()"<<endl;}
void show(int){cout<<"Base Show(int)"<<endl;}
~Base(){cout<<"~Base()"<<endl;}
protected:
int ma;
};
class Derive : public Base
{
public:
Derive(int data=20):Base(data),mb(data){
cout<<"Derive"<<endl;
}
void show(){cout<<"Derive Show()"<<endl;}
~Derive(){cout<<"~Derive()"<<endl;}
private:
int mb;
};
int main(){
Base b(10);
Derive d(20);
Base *pb =&d;
pb->show(); //調(diào)用的是基類(lèi)的 show
pb->show(100);//調(diào)用的是基類(lèi)的 show(int)
((Derive *)pb)->show(); //強(qiáng)轉(zhuǎn)后 調(diào)用的是派生類(lèi)的 show
}
基類(lèi)指針(引用) -> 派生類(lèi)對(duì)象 類(lèi)型由上向下轉(zhuǎn) NOT OK
Base b(10);
Derive d(20);
Derive *pb =&b;// NOT OK pb指針能夠訪(fǎng)問(wèn)的區(qū)域超過(guò)了實(shí)際對(duì)象b的內(nèi)存塊 ,危險(xiǎn)訪(fǎng)問(wèn)
代碼4
#include <iostream>
using namespace std;
class Base{
public:
Base(){
cout<<"Base()"<<endl;
}
void show(){
cout<<"Base show()"<<endl;
}
void show(int x){
cout<<"Base show(int x)"<<endl;
}
~Base(){
cout<<"~Base()"<<endl;
}
private:
int ma;
};
class Derive :public Base{
public:
Derive(){
cout<<"Derive()"<<endl;
}
void show(){
cout<<"Derive show()"<<endl;
}
~Derive(){
cout<<"~Derive()"<<endl;
}
private:
int ma;
};
int main(){
Derive d;
Derive *pd=&d;
d.show();
d.show(100); //編譯報(bào)錯(cuò), Derive 的void show()方法把Base 的void show() void show(int x) 都隱藏了
pd->show(100);//編譯報(bào)錯(cuò) Derive 的void show()方法把Base 的void show() void show(int x) 都隱藏了
return 0;
}
代碼5
#include <iostream>
using namespace std;
class Base{
public:
Base(){
cout<<"Base()"<<endl;
}
virtual void show(){
cout<<"Base show()"<<endl;
}
void show(int x){
cout<<"Base show(int x)"<<endl;
}
~Base(){
cout<<"~Base()"<<endl;
}
private:
int ma;
};
class Derive :public Base{
public:
Derive(){
cout<<"Derive()"<<endl;
}
virtual void show(){
cout<<"Derive show()"<<endl;
}
~Derive(){
cout<<"~Derive()"<<endl;
}
private:
int ma;
};
int main(){
Derive *pd=new Derive();
pd->show(100); //編譯報(bào)錯(cuò),Derive 中的show() 函數(shù),只要名字與Base中有相同名字的函數(shù)的,就會(huì)隱藏掉Base中所有的show方法(不管加不加virtual),包括void show() void show(int x)
return 0;
}到此這篇關(guān)于淺析C++中的重載,隱藏和覆蓋的文章就介紹到這了,更多相關(guān)C++重載 隱藏 覆蓋內(nèi)容請(qǐng)搜索腳本之家以前的文章或繼續(xù)瀏覽下面的相關(guān)文章希望大家以后多多支持腳本之家!
相關(guān)文章
從匯編看c++中默認(rèn)構(gòu)造函數(shù)的使用分析
c++中,如果為一個(gè)類(lèi)沒(méi)有明確定義一個(gè)構(gòu)造函數(shù),那么,編譯器就會(huì)自動(dòng)合成一個(gè)默認(rèn)的構(gòu)造函數(shù)。下面,通過(guò)匯編程序,來(lái)看一下其真實(shí)情況2013-05-05
通過(guò)實(shí)例詳解C語(yǔ)言函數(shù)返回值
函數(shù)的返回值是指函數(shù)被調(diào)用之后,執(zhí)行函數(shù)體中的程序段所取得的并返回給主調(diào)函數(shù)的值,下面這篇文章主要給大家介紹了關(guān)于C語(yǔ)言函數(shù)返回值的相關(guān)資料,需要的朋友可以參考下2022-01-01
C語(yǔ)言計(jì)算Robots機(jī)器人行走路線(xiàn)
這篇文章介紹了C語(yǔ)言計(jì)算Robots機(jī)器人行走路線(xiàn),對(duì)大家的學(xué)習(xí)或者工作具有一定的參考學(xué)習(xí)價(jià)值,需要的朋友們下面隨著小編來(lái)一起學(xué)習(xí)學(xué)習(xí)吧2021-12-12
char str[] 與 char *str的區(qū)別詳細(xì)解析
以下是對(duì)char str[]與char *str的區(qū)別進(jìn)行了詳細(xì)的介紹,需要的朋友可以過(guò)來(lái)參考下2013-09-09
C++編程中new運(yùn)算符的使用學(xué)習(xí)教程
這篇文章主要介紹了C++編程中new運(yùn)算符的使用學(xué)習(xí)教程,是C++入門(mén)學(xué)習(xí)中的基礎(chǔ)知識(shí),需要的朋友可以參考下2016-01-01
C++?構(gòu)造函數(shù)和析構(gòu)函數(shù)(Constructors?&?Destructors)詳解
由于global?object的誕生比程序進(jìn)入更早點(diǎn),所以global?object的constructor執(zhí)行的時(shí)間更早于程序的進(jìn)入點(diǎn),所謂的default?constructor就是沒(méi)有指定任何的參數(shù)的constructor,這篇文章主要介紹了C++?構(gòu)造函數(shù)和析構(gòu)函數(shù)的相關(guān)知識(shí),需要的朋友可以參考下2024-05-05
C語(yǔ)言 詳細(xì)講解接續(xù)符和轉(zhuǎn)義符的使用
接續(xù)符是用來(lái)告訴編譯器行為的符號(hào),那編譯器遇到接續(xù)符是什么行為呢,就是去掉接續(xù)符,然后把下一行連接到現(xiàn)在這行上面,轉(zhuǎn)義符是主要用于表示無(wú)回顯字符,也用于表示常規(guī)字符,轉(zhuǎn)義符必須放在單引號(hào)或者雙引號(hào)里面2022-04-04
Pipes實(shí)現(xiàn)LeetCode(192.單詞頻率)
這篇文章主要介紹了Pipes實(shí)現(xiàn)LeetCode(192.單詞頻率),本篇文章通過(guò)簡(jiǎn)要的案例,講解了該項(xiàng)技術(shù)的了解與使用,以下就是詳細(xì)內(nèi)容,需要的朋友可以參考下2021-08-08
基于C語(yǔ)言實(shí)現(xiàn)學(xué)生成績(jī)管理系統(tǒng)
這篇文章主要介紹了基于C語(yǔ)言實(shí)現(xiàn)學(xué)生成績(jī)管理系統(tǒng),具有一定的參考價(jià)值,感興趣的小伙伴們可以參考一下2018-01-01

