Clean C++:私有化覆寫的虛函數(shù)

C++11中增加了override的關(guān)鍵字践樱,當(dāng)子類需要覆寫基類的虛函數(shù)時(shí)忽洛,提供顯式的override,可以有效改善程序的編譯時(shí)安全。

編譯時(shí)安全

例如饰躲,存在一個(gè)基類Test丁寄,它聲明了2個(gè)抽象方法屑埋。

struct TestResult;

struct Test {
  virtual void run(TestResult&) = 0;
  virtual int countTestCases() const = 0;

  virtual ~Test() {}
};

在子類中覆寫基類抽象方法時(shí),顯式地標(biāo)注override不僅可以增強(qiáng)代碼的可讀性,而且可以增強(qiáng)編譯時(shí)的安全性。如果嚴(yán)格遵循該規(guī)則洪鸭,當(dāng)重構(gòu)基類的抽象方法的簽名時(shí),編譯器可以準(zhǔn)確地找到所有編譯失敗的引用點(diǎn),提供了絕佳的重構(gòu)防護(hù)作用辖源。

#include "cut/core/test.h"

struct TestDecorator : Test { 
  TestDecorator(Test& test);

private: 
  void run(TestResult&) override;
  int countTestCases() const override;

private:
  Test& test; 
};

按接口編程

「按接口編程」是面向?qū)ο蟮闹匾瓌t。遵守該原則坞嘀,不僅使得客戶代碼依賴于更加穩(wěn)定的抽象继准,而且縮小了所依賴的范圍,使得客戶與實(shí)現(xiàn)更加正交陈瘦,從而實(shí)現(xiàn)解耦皱埠。在C++語言中诀黍,訪問控制和多態(tài)覆寫行為是分離的也颤,子類是可以覆寫父類私有的虛函數(shù)的燥翅。例如,模板方法的模式的典型實(shí)現(xiàn)方法姐霍,都是覆寫基類的私有的虛函數(shù)實(shí)現(xiàn)的恨胚。

私有化覆寫的虛函數(shù)骂因,可以有效保證用戶錯(cuò)誤地調(diào)用子類覆寫的成員函數(shù),暗示用戶應(yīng)該基于抽象的接口類型實(shí)施編程页屠。例如,上例TestDecorator的構(gòu)造函數(shù)必須公開镐捧,否則該類型的實(shí)例就不可構(gòu)造了玩焰。其覆寫的所有虛函數(shù)都被聲明為private荤西,警示用戶應(yīng)該基于Test在運(yùn)行時(shí)多態(tài)地調(diào)用相應(yīng)的抽象方法。

TestSuite: Test實(shí)例集的倉(cāng)庫(kù)實(shí)現(xiàn)

TestSuite為例冠句,它持有一系列Test類型的實(shí)例轻掩,它們的運(yùn)行時(shí)類型可能是TestCase, TestSuite, TestDecorator等等∨车祝基于抽象的Test類型坠狡,實(shí)現(xiàn)用例集的隱式樹型結(jié)構(gòu)舀凛。

#include "cut/core/test.h"
#include "cut/core/internal/bare_test_suite.h"
#include <vector>

struct TestSuite : Test, private BareTestSuite {
  ~TestSuite();

  void add(Test* test);

private:
  void run(TestResult& result) override;
  int countTestCases() const override;

private:
  const Test& get() const override;
  void runBare(TestResult& result) override;

private:
  std::vector<Test*> tests;
};

TestSuite在實(shí)現(xiàn)析構(gòu)函數(shù)及其其他函數(shù)時(shí),都是基于Test的抽象類型實(shí)現(xiàn)運(yùn)行時(shí)多態(tài)調(diào)用的。

#include "cut/core/test_suite.h"
#include "cub/base/algo.h"

void TestSuite::add(Test* test) {
  tests.push_back(test);
}

TestSuite::~TestSuite() {
  for (auto test : tests) {
    delete test;
  }
}

int TestSuite::countTestCases() const {
  static auto accumulator = [](Test* test){
    return test->countTestCases();
  };
  return cub::reduce(tests, 0, accumulator);
}

const Test& TestSuite::get() const {
  return *this;
}

void TestSuite::runBare(TestResult& result) {
  for (Test* test : tests) {
    test->run(result);
  }
}

void TestSuite::run(TestResult& result) {
  result.runTestSuite(*this);
}

Test, TestSuite, TestCase, TestDecorator之間的關(guān)系如下圖所示昧旨。

隱式樹:組合與修飾

最后編輯于
?著作權(quán)歸作者所有,轉(zhuǎn)載或內(nèi)容合作請(qǐng)聯(lián)系作者
  • 序言:七十年代末,一起剝皮案震驚了整個(gè)濱河市成玫,隨后出現(xiàn)的幾起案子绿渣,更是在濱河造成了極大的恐慌,老刑警劉巖根灯,帶你破解...
    沈念sama閱讀 218,284評(píng)論 6 506
  • 序言:濱河連續(xù)發(fā)生了三起死亡事件径缅,死亡現(xiàn)場(chǎng)離奇詭異掺栅,居然都是意外死亡,警方通過查閱死者的電腦和手機(jī)纳猪,發(fā)現(xiàn)死者居然都...
    沈念sama閱讀 93,115評(píng)論 3 395
  • 文/潘曉璐 我一進(jìn)店門氧卧,熙熙樓的掌柜王于貴愁眉苦臉地迎上來,“玉大人氏堤,你說我怎么就攤上這事沙绝。” “怎么了鼠锈?”我有些...
    開封第一講書人閱讀 164,614評(píng)論 0 354
  • 文/不壞的土叔 我叫張陵闪檬,是天一觀的道長(zhǎng)。 經(jīng)常有香客問我购笆,道長(zhǎng)粗悯,這世上最難降的妖魔是什么? 我笑而不...
    開封第一講書人閱讀 58,671評(píng)論 1 293
  • 正文 為了忘掉前任同欠,我火速辦了婚禮样傍,結(jié)果婚禮上,老公的妹妹穿的比我還像新娘铺遂。我一直安慰自己铭乾,他們只是感情好,可當(dāng)我...
    茶點(diǎn)故事閱讀 67,699評(píng)論 6 392
  • 文/花漫 我一把揭開白布娃循。 她就那樣靜靜地躺著炕檩,像睡著了一般。 火紅的嫁衣襯著肌膚如雪捌斧。 梳的紋絲不亂的頭發(fā)上笛质,一...
    開封第一講書人閱讀 51,562評(píng)論 1 305
  • 那天,我揣著相機(jī)與錄音捞蚂,去河邊找鬼妇押。 笑死,一個(gè)胖子當(dāng)著我的面吹牛姓迅,可吹牛的內(nèi)容都是我干的敲霍。 我是一名探鬼主播,決...
    沈念sama閱讀 40,309評(píng)論 3 418
  • 文/蒼蘭香墨 我猛地睜開眼丁存,長(zhǎng)吁一口氣:“原來是場(chǎng)噩夢(mèng)啊……” “哼肩杈!你這毒婦竟也來了?” 一聲冷哼從身側(cè)響起解寝,我...
    開封第一講書人閱讀 39,223評(píng)論 0 276
  • 序言:老撾萬榮一對(duì)情侶失蹤扩然,失蹤者是張志新(化名)和其女友劉穎,沒想到半個(gè)月后聋伦,有當(dāng)?shù)厝嗽跇淞掷锇l(fā)現(xiàn)了一具尸體夫偶,經(jīng)...
    沈念sama閱讀 45,668評(píng)論 1 314
  • 正文 獨(dú)居荒郊野嶺守林人離奇死亡界睁,尸身上長(zhǎng)有42處帶血的膿包…… 初始之章·張勛 以下內(nèi)容為張勛視角 年9月15日...
    茶點(diǎn)故事閱讀 37,859評(píng)論 3 336
  • 正文 我和宋清朗相戀三年,在試婚紗的時(shí)候發(fā)現(xiàn)自己被綠了兵拢。 大學(xué)時(shí)的朋友給我發(fā)了我未婚夫和他白月光在一起吃飯的照片翻斟。...
    茶點(diǎn)故事閱讀 39,981評(píng)論 1 348
  • 序言:一個(gè)原本活蹦亂跳的男人離奇死亡,死狀恐怖说铃,靈堂內(nèi)的尸體忽然破棺而出访惜,到底是詐尸還是另有隱情,我是刑警寧澤截汪,帶...
    沈念sama閱讀 35,705評(píng)論 5 347
  • 正文 年R本政府宣布疾牲,位于F島的核電站植捎,受9級(jí)特大地震影響衙解,放射性物質(zhì)發(fā)生泄漏。R本人自食惡果不足惜焰枢,卻給世界環(huán)境...
    茶點(diǎn)故事閱讀 41,310評(píng)論 3 330
  • 文/蒙蒙 一蚓峦、第九天 我趴在偏房一處隱蔽的房頂上張望。 院中可真熱鬧济锄,春花似錦暑椰、人聲如沸。這莊子的主人今日做“春日...
    開封第一講書人閱讀 31,904評(píng)論 0 22
  • 文/蒼蘭香墨 我抬頭看了看天上的太陽。三九已至低滩,卻和暖如春召夹,著一層夾襖步出監(jiān)牢的瞬間,已是汗流浹背恕沫。 一陣腳步聲響...
    開封第一講書人閱讀 33,023評(píng)論 1 270
  • 我被黑心中介騙來泰國(guó)打工监憎, 沒想到剛下飛機(jī)就差點(diǎn)兒被人妖公主榨干…… 1. 我叫王不留,地道東北人婶溯。 一個(gè)月前我還...
    沈念sama閱讀 48,146評(píng)論 3 370
  • 正文 我出身青樓鲸阔,卻偏偏與公主長(zhǎng)得像,于是被迫代替她去往敵國(guó)和親迄委。 傳聞我的和親對(duì)象是個(gè)殘疾皇子褐筛,可洞房花燭夜當(dāng)晚...
    茶點(diǎn)故事閱讀 44,933評(píng)論 2 355

推薦閱讀更多精彩內(nèi)容

  • 1. 析構(gòu)函數(shù)和虛析構(gòu)函數(shù) 如果基類的析構(gòu)函數(shù)是虛的,那么它的派生類的析構(gòu)函數(shù)都是虛的 這將導(dǎo)致:當(dāng)派生類析構(gòu)的時(shí)...
    杰倫哎呦哎呦閱讀 2,488評(píng)論 0 2
  • C++虛函數(shù) C++虛函數(shù)是多態(tài)性實(shí)現(xiàn)的重要方式叙身,當(dāng)某個(gè)虛函數(shù)通過指針或者引用調(diào)用時(shí)死讹,編譯器產(chǎn)生的代碼直到運(yùn)行時(shí)才...
    小白將閱讀 1,742評(píng)論 4 19
  • 二十.多態(tài)與虛函數(shù) 多態(tài):多態(tài)按字面的意思就是多種形態(tài)。當(dāng)類之間存在層次結(jié)構(gòu)曲梗,并且類之間是通過繼承關(guān)聯(lián)時(shí)赞警,就會(huì)用到...
    b83dcb2e8b71閱讀 600評(píng)論 0 1
  • 收集非原創(chuàng)文章妓忍,如遇原作者,請(qǐng)私聊我愧旦,我會(huì)表明出處世剖! 1--10 1. C++中什么數(shù)據(jù)分配在棧或堆笤虫,靜態(tài)存儲(chǔ)區(qū)以...
    Juinjonn閱讀 4,940評(píng)論 0 30
  • 轉(zhuǎn)成早班之后旁瘫,身體的生物鐘還沒有完全扭轉(zhuǎn)回來,哪怕每天晚上及時(shí)睡覺琼蚯,也依然要在第二天下午休息的時(shí)候睡上一會(huì)兒酬凳。 狀...
    南船北巷閱讀 171評(píng)論 0 1