• <ins id="pjuwb"></ins>
    <blockquote id="pjuwb"><pre id="pjuwb"></pre></blockquote>
    <noscript id="pjuwb"></noscript>
          <sup id="pjuwb"><pre id="pjuwb"></pre></sup>
            <dd id="pjuwb"></dd>
            <abbr id="pjuwb"></abbr>

              C++博客 :: 首頁 :: 聯系 ::  :: 管理
              163 Posts :: 4 Stories :: 350 Comments :: 0 Trackbacks

            常用鏈接

            留言簿(48)

            我參與的團隊

            搜索

            •  

            積分與排名

            • 積分 - 401318
            • 排名 - 59

            最新評論

            閱讀排行榜

            評論排行榜

            設想在一個軍事應用程序里,有一個表示敵人目標的類:

            class enemytarget

            {
            public:
              enemytarget() { ++numtargets; }
              enemytarget(const enemytarget&) { ++numtargets; }
              ~enemytarget() { --numtargets; }

              static size_t numberoftargets()
              { return numtargets; }

              virtual bool destroy();         // 摧毀enemytarget對象后
                                                          // 返回成功

            private:
              static size_t numtargets;     // 對象計數器
            };

             

            //類的靜態成員要在類外定義;
            // 缺省初始化為0

            size_t enemytarget::numtargets;

            敵人的坦克是一種特殊的敵人目標,所以會很自然地想到將它抽象為一個以公有繼承方式從enemytarget派生出來的類。因為不但要關心敵人目標的總數,也要關心敵人坦克的總數,所以和基類一樣,在派生類里也采用了上面提到的同樣的技巧:

            class enemytank: public enemytarget {
            public:
              enemytank() { ++numtanks; }

              enemytank(const enemytank& rhs)
              : enemytarget(rhs)
              { ++numtanks; }

              ~enemytank() { --numtanks; }

              static size_t numberoftanks()
              { return numtanks; }

              virtual bool destroy();

            private:
              static size_t numtanks;         // 坦克對象計數器
            };

             

            最后,假設程序的其他某處用new動態創建了一個enemytank對象,然后用delete刪除掉:

            enemytarget *targetptr = new enemytank;

            ...

            delete targetptr

              這樣會發生嚴重問題,因為c++語言標準關于這個問題的闡述非常清楚:當通過基類的指針去刪除派生類的對象,而基類又沒有虛析構函數時,結果將是不可確定的。實際運行時經常發生的是,派生類的析構函數永遠不會被調用。在本例中,這意味著當targetptr 刪除時,enemytank的數量值不會改變,那么,敵人坦克的數量就是錯的。

            如果某個類不包含虛函數,那一般是表示它將不作為一個基類來使用。當一個類不準備作為基類使用時,使析構函數為虛一般是個壞主意。因為它會為類增加一個虛函數表,使得對象的體積翻倍,還有可能降低其可移植性。

            所以基本的一條是:無故的聲明虛析構函數和永遠不去聲明一樣是錯誤的。實際上,很多人這樣總結:當且僅當類里包含至少一個虛函數的時候才去聲明虛析構函數。

            抽象類是準備被用做基類的,基類必須要有一個虛析構函數,純虛函數會產生抽象類,所以方法很簡單:在想要成為抽象類的類里聲明一個純虛析構函數。

            這里是一個例子:

            class awov {                // awov = "abstract w/o
                                               // virtuals"
            public:
              virtual ~awov() = 0;      // 聲明一個純虛析構函數
            };

            這個類有一個純虛函數,所以它是抽象的,而且它有一個虛析構函數,所以不會產生析構函數問題。但這里還有一件事:必須提供純虛析構函數的定義:

            awov::~awov() {}           // 純虛析構函數的定義

            這個定義是必需的,因為虛析構函數工作的方式是:最底層的派生類的析構函數最先被調用,然后各個基類的析構函數被調用。這就是說,即使是抽象類,編譯器也要產生對~awov的調用,所以要保證為它提供函數體。如果不這么做,鏈接器就會檢測出來,最后還是得回去把它添上。

            注意:如果聲明虛析構函數為inline,將會避免調用它們時產生的開銷,但編譯器還是必然會在什么地方產生一個此函數的拷貝。

            posted on 2008-01-22 11:39 sdfasdf 閱讀(8643) 評論(4)  編輯 收藏 引用 所屬分類: C++

            Feedback

            # re: Effective C++學習筆記:確定基類有虛析構函數 2008-01-22 17:48 minidxer
            這樣寫點自己的體會并沒什么不好的,只是作者在選擇發在首頁的時候好好考慮一下就是了。
            LS的說話還是文明一些比較好  回復  更多評論
              

            # re: Effective C++學習筆記:確定基類有虛析構函數 2010-03-30 23:01 kddsly
            最底層的派生類的析構函數最先被調用,然后各個基類的析構函數被調用.
            這句話是不是說反了,不是先基類的析構被調用,然后才是派生類的被調用嗎?   回復  更多評論
              

            # re: Effective C++學習筆記:確定基類有虛析構函數 2011-01-20 10:14 SS
            奇怪啊,好像純虛函數是不能被定義的吧,為什么還可以
            awov::~awov() {} // 純虛析構函數的定義

              回復  更多評論
              

            # re: Effective C++學習筆記:確定基類有虛析構函數 2012-01-13 05:19 Jocuri online
            好的網站  回復  更多評論
              

            97热久久免费频精品99| 久久人妻少妇嫩草AV无码蜜桃| 无码人妻少妇久久中文字幕蜜桃| 午夜天堂av天堂久久久| 久久综合久久综合久久| 伊人久久大香线蕉综合5g| 狠狠88综合久久久久综合网| 国产免费久久精品丫丫| 99久久无色码中文字幕人妻| 久久99精品久久久久久不卡| 久久午夜无码鲁丝片| 亚洲欧美日韩精品久久亚洲区 | 狠狠色丁香久久综合五月| 国产精品久久婷婷六月丁香| 91精品国产高清久久久久久io | 91精品国产9l久久久久| 亚洲第一永久AV网站久久精品男人的天堂AV| 久久久久亚洲国产| 日韩亚洲国产综合久久久| 99久久国产免费福利| 99久久成人国产精品免费| 亚洲欧洲久久久精品| 久久亚洲天堂| 亚洲午夜福利精品久久| 青青久久精品国产免费看| 久久播电影网| 久久久噜噜噜久久| 久久男人AV资源网站| 精品久久久久久无码中文野结衣| 欧美激情精品久久久久| 91精品国产色综久久 | 久久超乳爆乳中文字幕| 久久久久亚洲AV成人片| 久久久久亚洲AV无码网站| 久久亚洲日韩精品一区二区三区| 久久精品亚洲AV久久久无码| 亚洲综合精品香蕉久久网| 蜜臀久久99精品久久久久久小说 | 一本色综合久久| 97精品依人久久久大香线蕉97 | 青青青国产成人久久111网站|