C++——派生類中的訪問——可見性問題

 

 

C++中派生類對基類成員的訪問形式主要有如下兩種:
一、內部訪問:由派生類中新增成員對基類繼承來的成員的訪問。
二、對象訪問:在派生類外部,經過派生類的對象對從基類繼承來的成員的訪問。今天給你們介紹在3中繼承方式下,派生類對基類成員的訪問規則。
一、私有繼承的訪問規則
當類的繼承方式爲私有繼承時,基類的public成員和protected成員被繼承後成爲派生類的private成員,派生類的其它成員能夠直接訪問它們,可是在類的外部經過派生類的對象沒法訪問。基類的private成員在私有派生類中是不可直接訪問的,因此不管是派生類的成員仍是經過派生類的對象,都沒法直接訪問從基類繼承來的private成員,可是能夠經過基類提供的public成員函數間接訪問。私有繼承的訪問規則總結以下:
基類成員 private成員 public成員 protected成員
內部訪問 不可訪問 可訪問 可訪問
對象訪問 不可訪問 不可訪問 不可訪問函數

二、公有繼承的訪問規則
當類的繼承方式爲公有繼承時,基類的public成員和protected成員被繼承到派生類中仍做爲派生類的public成員和protected成員,派生類的其它成員能夠直接訪問它們。可是,類的外部使用者只能經過派生類的對象訪問繼承來的public成員。基類的private成員在私有派生類中是不可直接訪問的,因此不管是派生類成員仍是派生類的對象,都沒法直接訪問從基類繼承來的private成員,可是能夠經過基類提供的public成員函數直接訪問它們。公有繼承的訪問規則總結以下:
基類成員 private成員 public成員 protected成員
內部訪問 不可訪問 可訪問 可訪問
對象訪問 不可訪問 可訪問 不可訪問對象

三、保護繼承的訪問規則
當類的繼承方式爲保護繼承時,基類的public成員和protected成員被繼承到派生類中都做爲派生類的protected成員,派生類的其它成員能夠直接訪問它們,可是類的外部使用者不能經過派生類的對象訪問它們。基類的private成員在私有派生類中是不可直接訪問的,因此不管是派生類成員仍是經過派生類的對象,都沒法直接訪問基類中的private成員。保護繼承的訪問規則總結以下:
基類成員 private成員 public成員 protected成員
內部訪問 不可訪問 可訪問 可訪問
對象訪問 不可訪問 不可訪問 不可訪問繼承

 

派生類中的訪問——可見性問題內存

一、 對於在不一樣做用域聲明的標識符,可見性原則:
若存在兩個或多個具備包含關係的做用域,外層聲明瞭一個標識符,而內層沒有再次聲明同名標識符,則外層標識符在內層仍然可見;
若在內層聲明瞭同名標識符,則外層標識符在內層不可見,這時內層變量隱藏了外層的同名變量,這種現象稱爲隱藏規則。
其中,外層爲基類,內層爲派生類。作用域

二、 做用域:
使用::做用域限定要訪問的成員所在類的名稱。
基類和派生類新增的成員都具備類做用域,但做用範圍不一樣:是相互保護的兩個層,派生類在內層。
(1)單繼承中的同名隱藏
在沒有使用虛函數的狀況下,若派生類聲明瞭一個和基類成員同名的新成員函數,即便函數的參數表不一樣,那麼從基類繼承的同名函數的全部重載形式也都被隱藏(外層基類中的同名成員函數被隱藏),使用成員名只能訪問到派生類的成員函數。若要訪問被隱藏的基類成員,必須使用基類名和做用域符::限定,使用基類名::成員名訪問。
隱藏規則在私有繼承中的應用
在私有繼承時,爲保證基類的公有成員能在派生類中訪問,必須在派生類中從新聲明同名的成員。在調用時,根據同名隱藏的規則,使用派生類中的函數。若對基類繼承過來的某些函數功能進行擴充和改造,能夠經過隱藏實現。
(2)多繼承中的同名隱藏及訪問衝突問題
①各基類沒有任何繼承關係,同時沒有共同基類的狀況:

在沒有使用虛函數的狀況下,若派生類的多個基類擁有同名的成員,同時派生類又新增了同名的成員函數時,派生類將隱藏全部基類的同名函數。
隱藏訪問及隱藏衝突:
A 使用「對象名.成員名」可惟一標識和訪問新增派生類成員;——隱藏
B 只有使用「對象名.基類名::成員名」這種做用域標識符能夠訪問基類的同名成員;
C若派生類沒有聲明同名函數,使用「對象名.成員名」沒法惟一標示成員——衝突!
只能經過「對象名.基類名::成員名」訪問基類的成員。

② 有間接基類的狀況
A
B1 B2
C
對於派生類C,其直接基類B一、B2,間接基類A。
若B1 B2分別定義了同名的成員,而派生類C沒有新增該同名函數,則使用「類C的對象名.成員名」產生衝突!只能使用「類C的對象名.B1/B2::成員名」能夠訪問B1/B2中的同名成員;但任何方式都沒法訪問A中的同名成員。(同①)
若要訪問類A中的成員,而在B1 B 2 C中沒有新增同名的成員,經過「類C的對象名.A中成員名」或「類C的對象名.A::A中成員名」訪問類A中的成員,產生衝突!只有經過
「類C的對象名.B1/B2::成員名」訪問類A中的成員。
若派生類C聲明瞭同名函數,則使用「類C的對象名.成員名」訪問的是C類新增的同名成員函數——隱藏

小結:
同名成員的惟一標識問題:
•使用做用域符::惟一標識派生類中由直接基類繼承的成員;
派生類對象.直接基類名::同名成員/同名成員函數
•將共同基類設置爲虛基類,這時從不一樣的路徑繼承過來的同名成員在內存中只要一個拷貝,同一個函數也只有一個路徑。聲明虛基類是在派生類定義過程當中進行的:
class 派生類名:virtual 繼承方式 基類名class

相關文章
相關標籤/搜索