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

2021-08-04 21:38:49 字數 1155 閱讀 5775

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 類的公有繼承,基類的私有成員在派生類中不可見或不可訪問

在c 語言中,一個派生類可以從一個基類派生,也可以從多個基類派生。從一個基類派生的繼承稱為單繼承 從多個基類派生的繼承稱為多繼承。方式如下 公有繼承 public 私有繼承 private 保護繼承 protected 是常用的三種繼承方式。1.公有繼承 public 公有繼承的特點是基類的公有成員...

C 中在基類裡宣告為const的純虛擬函式在派生類裡的同名函

必須,函式是否為const也是過載條件之一比如在一個類裡,存在重名函式 void print void print const 那麼是合法的過載 但是如果是 int print const int print 則不是合法過載 因此想要實體化circle類,必須實現一個形如double print c...

關於C中建構函式的繼承的問題,請教c 有參建構函式繼承的問題

1 建構函式不繼承,派生類會自動呼叫基類建構函式。2 若類內沒有定義建構函式,系統會自動隱式生成一個不帶引數的建構函式,比如定義一個類 public class a 可以理解為它已經存在一個如下的建構函式 public class a 3 派生類建構函式自動呼叫基類的不帶引數的建構函式,注意下面的格...