• <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>

            MyMSDN

            MyMSDN記錄開(kāi)發(fā)新知道

            關(guān)于C++ Template分離頭文件和定義所產(chǎn)生的錯(cuò)誤

            編譯錯(cuò)誤

            如圖所示的代碼出現(xiàn)了如圖所示的錯(cuò)誤,誰(shuí)能解釋一下是為什么呢?

            雖然在最后include進(jìn)了cpp文件,而且這種做法也在C++ Primer中也是正確的(難道是標(biāo)準(zhǔn)和現(xiàn)實(shí)的差距?)。將代碼稍微變動(dòng),并將cpp部分的內(nèi)容移到.h文件中的include位置即可正確編譯。

            編譯正確

            posted on 2009-02-22 06:05 volnet 閱讀(4331) 評(píng)論(20)  編輯 收藏 引用

            評(píng)論

            # re: 關(guān)于C++ Template分離頭文件和定義所產(chǎn)生的錯(cuò)誤 2009-02-22 09:12 huoxd

            我記著這是個(gè)老問(wèn)題了,的確不少的參考書(shū)中這么說(shuō)過(guò),但是要注意兩點(diǎn):
            1.這樣的分離只是文件層面的分離,并非是傳統(tǒng)的模塊之間只見(jiàn)接口,不見(jiàn)實(shí)現(xiàn)的分離,做為沒(méi)用動(dòng)態(tài)特性的靜態(tài)語(yǔ)言,C++把模板的實(shí)現(xiàn)封裝成二進(jìn)制是不可能的,這種編程技巧只是為了讓代碼瀏覽起來(lái)感覺(jué)更規(guī)范.
            2.不同的編譯器對(duì)模板的實(shí)現(xiàn)還沒(méi)有完全按照標(biāo)準(zhǔn)來(lái)支持,所以產(chǎn)生錯(cuò)誤了不奇怪.  回復(fù)  更多評(píng)論   

            # re: 關(guān)于C++ Template分離頭文件和定義所產(chǎn)生的錯(cuò)誤 2009-02-22 09:14 huoxd

            是"沒(méi)有動(dòng)態(tài)特性"的,打錯(cuò)了,不好意思  回復(fù)  更多評(píng)論   

            # re: 關(guān)于C++ Template分離頭文件和定義所產(chǎn)生的錯(cuò)誤 2009-02-22 12:04 空明流轉(zhuǎn)

            在源代碼級(jí)別,模板是可以有一定程度的分離的.

            我舉個(gè)例子

            //lib.h
            template <class T> const T& return_itself(const T& val);

            //lib.cpp
            template <class T> const T& return_itself(const T& val){ return val; }
            void instantiate_return_itself(){
            //this is not executing factually.
            return_itself((int)0);
            }

            //app.cpp
            #include "lib.h"

            int main(){
            return_itself((int)0); // OK
            return_itself(0.0f); // no compiler error happens but some link errors
            }  回復(fù)  更多評(píng)論   

            # re: 關(guān)于C++ Template分離頭文件和定義所產(chǎn)生的錯(cuò)誤 2009-02-22 12:37 huoxd

            樓上說(shuō)的是模板函數(shù),的確可以分離,但模板類就不太容易了  回復(fù)  更多評(píng)論   

            # re: 關(guān)于C++ Template分離頭文件和定義所產(chǎn)生的錯(cuò)誤 2009-02-22 18:23 Dancefire

            樓主,你的問(wèn)題其實(shí)很簡(jiǎn)單。

            你是不是把foo.cpp也放進(jìn)Visual C++的項(xiàng)目里了?如果是的話,這樣會(huì)導(dǎo)致foo.cpp的編譯,這個(gè)編譯會(huì)導(dǎo)致T Foo<T>::GetInstance(void)被編譯實(shí)現(xiàn)。當(dāng)繼續(xù)編譯main.cpp的時(shí)候,就會(huì)報(bào)告,T Foo<T>::GetInstance(void)已經(jīng)有一個(gè)實(shí)例了。

            解決辦法很簡(jiǎn)單,把foo.cpp移出工程就可以了。只要物理上foo.h的同目錄存在foo.cpp這個(gè)文件就可以了。因?yàn)閒oo.cpp根本沒(méi)必要去編譯。甚至我都不建議你稱其為foo.cpp,不如叫什么foo_impl.hpp之類的文件名更合理些,這樣即使這個(gè)文件在工程里面也不回導(dǎo)致被編譯。  回復(fù)  更多評(píng)論   

            # re: 關(guān)于C++ Template分離頭文件和定義所產(chǎn)生的錯(cuò)誤 2009-02-22 19:36 chujun

            Foo.cpp里改成:
            #ifndef FOO_H_
            #include "foo.h"
            template<typename T> T Foo<T>::GetInstance() {
            return instance;
            }
            #endif
            可以試一下...  回復(fù)  更多評(píng)論   

            # re: 關(guān)于C++ Template分離頭文件和定義所產(chǎn)生的錯(cuò)誤 2009-02-22 20:57 yindf

            Dancefire 的答案是對(duì)的,如果你自己寫(xiě)makefile的話,肯定不能把foo.cpp編譯成foo.obj。

            書(shū)上沒(méi)有說(shuō)這一點(diǎn),但是你的IDE自動(dòng)幫你makefile了,所以有些時(shí)候,自動(dòng)化也有不好的地方呀。  回復(fù)  更多評(píng)論   

            # re: 關(guān)于C++ Template分離頭文件和定義所產(chǎn)生的錯(cuò)誤 2009-02-22 22:26 volnet

            @Dancefire
            的確,把foo.cpp移出項(xiàng)目外的話就可以順利編譯并執(zhí)行了!
            但是在你的回答中,為什么會(huì)提到“當(dāng)繼續(xù)編譯main.cpp的時(shí)候……”,這是為什么呢?為什么非模板類型就可以?  回復(fù)  更多評(píng)論   

            # re: 關(guān)于C++ Template分離頭文件和定義所產(chǎn)生的錯(cuò)誤 2009-02-22 23:11 空明流轉(zhuǎn)

            非模板類型的應(yīng)該也是不可以的。
            還有就是,不僅僅是模板函數(shù),模板類一樣可以。  回復(fù)  更多評(píng)論   

            # re: 關(guān)于C++ Template分離頭文件和定義所產(chǎn)生的錯(cuò)誤 2009-02-22 23:15 volnet

            @空明流轉(zhuǎn)
            我說(shuō)的可以是指在h中聲明,在cpp中定義,這顯然是可以的(也是標(biāo)準(zhǔn)的做法)
            模板函數(shù)和模板類的確都存在如本文所述的問(wèn)題,并且用Dancefire的方法,或者使用全部寫(xiě)在.h文件中的方式,都是可以的。  回復(fù)  更多評(píng)論   

            # re: 關(guān)于C++ Template分離頭文件和定義所產(chǎn)生的錯(cuò)誤 2009-02-23 00:49 Dancefire

            @volnet
            呵呵,非模板類型的函數(shù)定義我們也不會(huì)需要在foo.h中include foo.cpp啊:)

            在樓主的例子里面為了能夠讓定義和聲明分開(kāi),將聲明放到了foo.h中,而定義放到了foo.cpp中,這和非模板類型的函數(shù)是一樣的。但是可惜這么做是無(wú)法通過(guò)的,因?yàn)槟0孱愋秃瘮?shù)不能夠(由于沒(méi)有export支持)單獨(dú)編譯。為了讓編譯通過(guò),樓主將foo.cpp給include進(jìn)了foo.h,這樣實(shí)際上是將兩個(gè)文件整合成一個(gè)文件了。這樣編譯就沒(méi)有問(wèn)題了,但是得小心需要把foo.cpp分離出項(xiàng)目,因?yàn)樗豢梢员痪幾g;或者將其擴(kuò)展名從.cpp改為.hpp。

            實(shí)在是不推薦樓主這么分開(kāi)的寫(xiě),說(shuō)實(shí)話這算不上是什么標(biāo)準(zhǔn)的做法,而且這樣并沒(méi)有太大的意義。如果非要分開(kāi),可以將定義后綴到聲明后面,在一個(gè)文件里。但是分開(kāi)確實(shí)沒(méi)太大意義。可以研讀一下boost里面的做法。  回復(fù)  更多評(píng)論   

            # re: 關(guān)于C++ Template分離頭文件和定義所產(chǎn)生的錯(cuò)誤 2009-02-23 00:54 volnet

            @Dancefire
            原來(lái)你們說(shuō)的是include foo.cpp

            分開(kāi)有一個(gè)好處就是可以成套地替換吧,雖然通常我們不這么做,但是卻從語(yǔ)法上支持了這么做。如果可以當(dāng)然好了,不行的話肯定是沒(méi)辦法的。  回復(fù)  更多評(píng)論   

            # re: 關(guān)于C++ Template分離頭文件和定義所產(chǎn)生的錯(cuò)誤 2009-02-23 00:57 volnet

            @Dancefire
            boost在C++中的地位是什么呢?一個(gè)工業(yè)庫(kù)?一個(gè)泛型標(biāo)準(zhǔn)?一個(gè)開(kāi)源范例?它對(duì)C++學(xué)習(xí)有什么好處呢?  回復(fù)  更多評(píng)論   

            # re: 關(guān)于C++ Template分離頭文件和定義所產(chǎn)生的錯(cuò)誤 2009-02-23 01:17 Dancefire

            @volnet
            Boost可以稱其為是一套準(zhǔn)標(biāo)準(zhǔn)庫(kù)。它項(xiàng)目建立的目的之一就是為未來(lái)的C++標(biāo)準(zhǔn)庫(kù)提供候選方案,目前已經(jīng)有將近十個(gè)Boost庫(kù)成功的成為了C++標(biāo)準(zhǔn)預(yù)案。

            它的優(yōu)勢(shì)很多,首先是代碼使用現(xiàn)代C++的語(yǔ)法,因此namespace, 異常, 模板之類的C++特性會(huì)被充分挖掘利用,代碼從設(shè)計(jì)、實(shí)現(xiàn)到文檔都具有了相當(dāng)高的水準(zhǔn)。另外,由于它使用的是標(biāo)準(zhǔn)C++語(yǔ)法編寫(xiě),因此它的可移植性非常的好。當(dāng)然,針對(duì)一些存在問(wèn)題的編譯器,它也會(huì)進(jìn)行相應(yīng)的調(diào)整以盡量支持。

            Boost這種優(yōu)良的庫(kù),涵蓋的領(lǐng)域很廣,可以說(shuō)是標(biāo)準(zhǔn)庫(kù)很好的補(bǔ)充。另外絕大多數(shù)Boost庫(kù)都不需要編譯鏈接,大部分的Boost庫(kù)僅僅include頭文件即可工作。我看到國(guó)內(nèi)很多人提到Boost的時(shí)候說(shuō)它比較難以編譯安裝云云。其實(shí)沒(méi)必要編譯,絕大多數(shù)的庫(kù)僅僅是由頭文件組成的,只要include進(jìn)來(lái)就可以用了。

            Boost是C++強(qiáng)有力的工具,學(xué)習(xí)C++,除了標(biāo)準(zhǔn)語(yǔ)法和STL外,Boost是必須熟悉的,否則,工程上很有可能會(huì)做一些Boost已經(jīng)實(shí)現(xiàn)很久的東西,除了重復(fù)開(kāi)發(fā)外,而且你的代碼的質(zhì)量和可持續(xù)性比Boost差很遠(yuǎn),造成項(xiàng)目質(zhì)量的下降。  回復(fù)  更多評(píng)論   

            # re: 關(guān)于C++ Template分離頭文件和定義所產(chǎn)生的錯(cuò)誤 2009-02-23 01:22 volnet

            @Dancefire
            謝謝你對(duì)Boost做了詳細(xì)的介紹。
            那么,學(xué)習(xí)Boost庫(kù)需要有哪些準(zhǔn)備工作?(假設(shè)從初學(xué)者開(kāi)始)學(xué)習(xí)Boost庫(kù)又有哪些方法或者經(jīng)典的做法呢?(比如什么書(shū),或者什么文檔)  回復(fù)  更多評(píng)論   

            # re: 關(guān)于C++ Template分離頭文件和定義所產(chǎn)生的錯(cuò)誤 2009-02-23 13:29 maosher

            foo.h里面最下面倒數(shù)第二行

            的#include   回復(fù)  更多評(píng)論   

            # re: 關(guān)于C++ Template分離頭文件和定義所產(chǎn)生的錯(cuò)誤 2009-02-23 13:34 volnet

            @maosher
            怎么了?  回復(fù)  更多評(píng)論   

            # re: 關(guān)于C++ Template分離頭文件和定義所產(chǎn)生的錯(cuò)誤 2009-02-23 16:22 陳梓瀚(vczh)

            template特化是鏈接期不能解決的問(wèn)題,因此必須放進(jìn).h,不要使用別扭的技巧來(lái)分離。其實(shí)直接寫(xiě)在一個(gè)class{}里面反而漂亮得多。  回復(fù)  更多評(píng)論   

            # re: 關(guān)于C++ Template分離頭文件和定義所產(chǎn)生的錯(cuò)誤 2009-03-02 11:20 xcj

            簡(jiǎn)單的問(wèn)題。把foo.cpp中#include "foo.h"那行刪除掉應(yīng)該就沒(méi)問(wèn)題了。  回復(fù)  更多評(píng)論   

            # re: 關(guān)于C++ Template分離頭文件和定義所產(chǎn)生的錯(cuò)誤 2012-01-02 20:27 wzm

            .cpp 的模板前面加個(gè) export試試  回復(fù)  更多評(píng)論   


            只有注冊(cè)用戶登錄后才能發(fā)表評(píng)論。
            網(wǎng)站導(dǎo)航: 博客園   IT新聞   BlogJava   博問(wèn)   Chat2DB   管理


            特殊功能
             
            亚洲精品无码久久久影院相关影片| 女人香蕉久久**毛片精品| 亚洲国产另类久久久精品小说| 日本欧美久久久久免费播放网| 久久久久久免费一区二区三区| 人妻无码精品久久亚瑟影视| 国产婷婷成人久久Av免费高清| 国产视频久久| 久久久av波多野一区二区| 午夜精品久久久久9999高清| 国产精品久久免费| 亚洲国产精品无码久久| 久久综合一区二区无码| 94久久国产乱子伦精品免费| 精品人妻伦九区久久AAA片69| 久久99国产精品99久久| 性欧美丰满熟妇XXXX性久久久| 久久国产一片免费观看| 久久电影网一区| 久久国产色AV免费看| 亚洲欧美日韩中文久久| 怡红院日本一道日本久久 | 久久强奷乱码老熟女网站| 久久国产亚洲高清观看| 伊人久久大香线焦AV综合影院| 日韩十八禁一区二区久久| 99热成人精品免费久久| 色综合合久久天天综合绕视看| 人妻少妇久久中文字幕| 婷婷久久久亚洲欧洲日产国码AV| 亚洲精品无码专区久久同性男| 久久精品国产一区二区电影| 国产亚洲精午夜久久久久久| 久久这里只有精品久久| 久久99国产精品一区二区| 国产精品9999久久久久| 99蜜桃臀久久久欧美精品网站| 久久久久久亚洲精品影院| 狠狠色丁香婷婷久久综合| 久久人与动人物a级毛片| 久久久www免费人成精品|