在C 中,我的問題關於 基類有同名成員引起的二義性這個知識點

2021-08-04 21:39:52 字數 1155 閱讀 3947

1樓:匿名使用者

我來試著回答一下,大家看看是不是這樣:

1.原本語句列印「在a1中」;這個應該不用解釋,這個時候只有a1中存在print方法。

2.增加a2::print()函式後,由於a2繼承a1所以a2::

print()函式覆蓋(overwritten)a1::print()函式,所以這種情況下,對於a2及a2的所有子類的例項來說a1::print函式均是不可見的,所以這裡會列印「在a2中」

3.增加b1::print()函式後,b1::print又覆蓋了a2::print(),原理和第2條一樣,所以結果就是「在b1中」

4.增加b2::print()函式後,由於c同時繼承了b1和b2,所以b1::

print和b2::print在這裡產生了衝突,系統不知道應該呼叫b1::print還是b2::

print,所以程式無法編譯通過。

5.增加c::print函式後,呼叫c1.print結果非常明顯,就是呼叫c::print,這樣就消除了第4條中的二義性,所以又可以編譯通過了。

你程式中使用的虛基類並不能處理由b1和b2帶來的衝突,僅能處理由b1和b2的公共基類a2所帶來的衝突,當然這個程式中使用虛基類還是合理的。

2樓:mic大將軍

子類可以呼叫它的所有祖先的公有函式,如果它的祖先有重名的函式,那麼它使用離它最近的祖先的版本。如果它自己也定義了這個函式,則使用自己的版本。所以,你先只在a1中有print函式,那麼c使用的就是a1的版本。

接著你在a2中定義了,他比a1更接近c,將使用a2的版本。接著在b1中定義,將使用b1的版本。如果你在b2中也定義了,那麼b1和b2是同等接近c的,程式將不知道你要使用的是那個版本的。

最後在c中也定義了,那麼就會直接使用c的版本,不會查詢祖先中是否有這個函式,就不會報錯了。

3樓:匿名使用者

c直接繼承兩個父類b1,b2,這兩個裡面都有print方法

所以不新增語句4的時候調c1.print();程式不知道你到底要呼叫b1裡的還是b2裡的,會報錯,如果不進行呼叫,程式可正常編譯。

繼承的方法,如果有相同的函式,子類總是呼叫他父類中的那個函式,至於它父類的父類中的同名方法,他不去關心。

4樓:笨笨de世界

避免二義性的方法可以採用虛基類

C中關於類中臨時物件的問題

這個臨時物件是a 1000 產生的,並不是a作為臨時物件,a 1000 產生的物件又賦值給了a,臨時回物件用完就答 析構了。臨時物件一般是怎麼產生的呢,比如說你呼叫一個函式void fun test a 假設我們這樣呼叫 fun b 當呼叫的時候,往裡傳的這個b並不是真正的b,而是它會複製出一個和b...

關於c派生類中虛擬函式的問題,C 已經在派生類中重定義了抽象類中的純虛擬函式,為什麼還不讓我用派生類定義物件!?

如果是虛擬函式的話,在派生類中重新定義其函式體時,不會導致同名覆蓋.當用基類指標指向派生類物件並呼叫虛擬函式時,執行的是在派生類中重新定義的虛擬函式的函式體.虛擬函式必須要在基類用virtual修飾才能為虛擬函式,派生類若重定義該函專數,則無論是否有屬virtual關鍵字都是虛擬函式。你要判斷派生類...

關於C 6 0中的fun函式的問題,糾結死我了

fun函式怎麼能寫在主程式裡呢?應該先int a 1,b 5 然後cout fun a,b fun 寫在外面 int main int fun int a,int b 大概就是這樣 記得采納 樓上的基本思路正確,但是程式有基礎錯誤 1.函式需要提前宣告 2.整形求其絕對值用abs,fabs是求浮點數...