Item 9 絕不在構造和析構過程中呼叫虛函式

2021-08-01 20:11:59 字數 1262 閱讀 2871

這個應該是c++面試的經典題了,所以值得拿出來說一說

比如在乙個繼承體系中,基類的建構函式中呼叫了乙個基類的成員函式,你把它宣告為virtual,至少你在設計的時候是認為它有virtual屬性的。

class base

base::base()

class derivedone:public base

class derivedtwo: public base

接下來例項化物件,當我們執行

derivedone b;
因為derivedone是乙個派生類,那麼會先呼叫基類的建構函式base(),構造派生類中的基類子部分,但是這是base()函式呼叫的不是我們期望的derivedone中被override的函式,這就是問題所在,在基類構造期間,virtual函式不會下降到derived階層,這時virtual函式與普通類內成員函式等價,其實也很好理解,在構造基類期間,派生類根本沒有被構造出來,何來override之說?一直在derivedone物件被構造出來之前,b的型別都是base,可以通過typeiddynamic_cast驗證。

析構函式也是同樣的道理,析構的順序是自下而上的,所以當derived class被析構後,它的物件就不存在了,等到base class執行階段,virtual函式也就是基類本身的那個函式了,virtual屬性失去了意義。

如果希望建立乙個基類,執行時動態繫結適當的override函式,那麼一定不要在構造/析構函式中呼叫virtual,可以有其他的解決方案。

我們可以對期望函式通過引數傳遞資訊,然後再derived class建構函式的初始化列表中將資訊傳遞進去。

class base

base::base(const

string& s)

class derivedone:public base

絕不在構造和析構過程中呼叫虛函式

一 中心內容 因為類呼叫從不下降至派生類,導致若為純虛函式,則找不到函式的實現 若為非虛函式,則可能會導致呼叫錯誤的函式版本。二 內容簡介 考慮這樣一系列繼承 class transaction public transaction virtual void logtransaction const...

C 箴言 絕不在構造或析構期呼叫虛函式

文章內容請參加 以下是我自己寫的乙個測試用的例子 test.h ifndef test h define test h include class base protected virtual void init class inherit public base protected void in...

不在構造和析構過程中呼叫虛函式

1.不能在構造過程中呼叫虛函式。比如 在基類中有乙個虛函式。class transaction transaction transaction 基類建構函式實現 下面有兩個派生類繼承它 class buytransaction public transaction class selltransac...