3 回答
TA貢獻1865條經驗 獲得超7個贊
允許純虛擬析構函數的真正原因可能是,禁止它們意味著在語言中添加另一條規則,并且不需要此規則,因為允許純虛擬析構函數不會帶來任何不良影響。
不,普通的舊虛擬就足夠了。
如果使用默認實現為其虛擬方法創建對象,并希望使其抽象而不強迫任何人重寫任何特定方法,則可以將析構函數設為純虛擬。我看不出很多意義,但是有可能。
請注意,由于編譯器將為派生類生成隱式析構函數,因此,如果類的作者不這樣做,則任何派生類都不會是抽象的。因此,在基類中具有純虛擬析構函數不會對派生類產生任何影響。它只會使基類成為抽象類(感謝@kappa的注釋)。
人們可能還認為,每個派生類可能都需要具有特定的清理代碼,并使用純虛擬析構函數作為提示來編寫它,但這似乎是人為的(并且不強制執行)。
注意:析構函數是唯一的方法,即使它是純虛擬的,也必須具有實現才能實例化派生類(是的,純虛擬函數可以具有實現)。
struct foo {
virtual void bar() = 0;
};
void foo::bar() { /* default implementation */ }
class foof : public foo {
void bar() { foo::bar(); } // have to explicitly call default implementation.
};
TA貢獻1887條經驗 獲得超5個贊
您需要的抽象類至少是一個純虛函數。任何功能都可以;但是碰巧的是,析構函數是任何類都會擁有的東西-因此它始終是候選對象。此外,使析構函數為純虛擬的(而不是純虛擬的)除了使類抽象之外,沒有行為方面的副作用。因此,許多樣式指南建議始終使用純虛擬destuctor表示類是抽象的—如果出于其他原因,它提供了一致的位置,那么閱讀代碼的人可以查看該類是否是抽象的。
TA貢獻1796條經驗 獲得超4個贊
如果要創建抽象基類:
這不能被實例化(是的,這是多余的與術語“抽象”?。?/p>
但需要虛擬析構函數的行為(您打算攜帶指向ABC的指針,而不是指向派生類型的指針,并通過它們進行刪除)
但并不需要任何其他虛擬調度其他方法的行為(也許還有有沒有其他的方法呢?考慮一個簡單的受保護的“資源”的容器,它需要一個構造函數/析構函數/分配,但僅此而已)
...最簡單的方法是使析構函數成為純虛函數,并為其提供定義(方法主體),從而使類抽象。
對于我們假設的ABC:
您保證無法實例化它(即使是在類本身內部,這也就是為什么私有構造函數可能不夠用),您可以得到析構函數所需的虛擬行為,而不必查找和標記另一個不需要將虛擬調度作為“虛擬”。
- 3 回答
- 0 關注
- 1121 瀏覽
添加回答
舉報
