###問題 聲明和定義區別 definition declared 先看一下html
class B { private: A* m_pData; };
編譯很明顯出現錯誤::沒有 聲明 error: ‘A’ has not been declared error: 'A' does not name a typec++
class A; class B { private: A* m_pData; };
編譯沒有報錯 class A 屬於前置聲明 告訴編譯器 能夠識別這個符號聲明不會分配存儲空間 具體這符號能夠作什麼操做不清楚 The forward declaration tells the compiler that the said type exists and nothing more about the particular type 用處: 前置聲明用於指針和引用 由於指針是固定大小 不會由於類A的變更 引發類B從新編譯面試
class A;//這是前置聲明(Forward declaration) class B { private: A* m_pData; void test() { m_pData->test();//error以前沒有定義 } }; //自後定義了太晚啦 class A { public: void test(); };
編譯出現錯誤: 前置聲明不能被使用 a.cpp: In member function 'void B::test()': a.cpp:24:11: error: invalid use of incomplete type 'class A' m_pData->test(); ^ a.cpp:17:7: error: forward declaration of 'class A' why You cannot forward declare if you need to deference the structure members微信
class a 是作了聲明 並未定義(在使用以前)session
A.CPP: extern"C" long ABC( long a, long b ); //是聲明(不是定義 沒有給出 ABC實現的) void main() { long c = ABC( 10, 20 ); }
編譯沒有問題 運行期間出錯:函數
undefined symbol xxx工具
問題定位: nm a.out||grep xx |c++filt U AAA::BBB(int)ui
運行期間出錯: U 該符號未定義過,須要自其餘對象文件中連接進來.net
上面代碼在a.cpp中書寫,編譯生成文件a.obj,沒有問題。但按照以前的說明,鏈接時將錯誤,由於找不到符號_ABC。由於名字_ABC對應的地址欄還空着unix
緣由:對象(函數 類)沒有定義
通常緣由 1 該符號 沒有在當前cpp文件中實現 2 沒有引入其餘cpp文件(庫)
###回答:聲明和定義區別
聲明:定義一個符號 不佔用存儲空間 定義:對這這符號進行完整描述 具體到函數, class, 和基本數據類型 出現 {} 就是定義 定義的做用很明顯了,有意義的映射(名字 對地址)佔用存儲空間 A a;//屬於實例化 class A{}//聲明和定義合併在一塊兒了
聲明是告訴編譯器一些信息,以協助編譯器進行語法分析,避免編譯器報錯。而定義是告訴編譯器生成一些代碼,而且這些代碼將由鏈接器使用。即:聲明是給編譯器用的,定義是給鏈接器用的
用類來舉例
> class A { long ABC( long a, long b ); //只聲明,沒有定義 在cpp中實現 long get_session_( long a, long b ) { xxxx;} //定義 多了 {} 實現 };
####擴容:c++和c 對函數符號規則同樣嗎
說明 a.c 和a.cpp內容相同 代碼1
void test(); void test(int); void main() { }
代碼2 void test(){}; void test(int){}; void main() { }
1 gcc a.c 編譯代碼1沒有問題 由於聲明是符號
2 gcc a.c 編譯代碼2 有問題
3 g++ a.cpp: 代碼1和代碼2 編譯都沒有問題
c語言不支持函數的重載 由於函數名稱就是符號
知識補充 如何查找一個符號
**1 如何查看一個動態庫信息 **
1.nm -D libxxx.so 打印出符號信息。 我通常這樣用:nm -D libxxx.so |grep T 2.ldd libxxx.so 查看依賴關係 3.readelf -a libxxxx.so 用來讀取elf信息 我通常這樣用:readelf libxxx.so |grep NEEDED 這樣也能夠讀取依賴關係 4.objdump -d libxxxx.so 5.rmp -qfl libxxx.so 這樣能夠查看so庫裏面包含的內容,頭文件等 6.file libxxx.so 這樣能夠查看so庫的屬性 2 如何判斷動態庫a.so 是否load一個靜態庫b.a?
說明 1 ldd動態庫是不顯示靜態庫的名稱的
2 靜態庫的代碼在編譯過程當中已經被載入可執行程序 s
1 nm工具能夠打印出庫中的涉及到的全部符號,這裏的庫既能夠是靜態的也能夠是動態的。 2 可使用 ar -t libname.a 來查看一個靜態庫由那些.o文件構成
參考 1 http://stackoverflow.com/questions/10894804/forward-declaration-of-struct
2http://blog.chinaunix.net/uid-23381466-id-3464666.html
###想要了解更多c++面試考察基礎知識 歡迎關注