使用的環境是VS2008 + sp1.個人覺得這個版本的vs是M$的巔峰之作。功能全、運行速度快、不吃太多的內存。vs10就太慢了,不過vs12還是蠻清爽的,雖然也因為提示功能被多吃了200M+的內存。這個系列的文章主要是講解Vc++的工程屬性。不涉及任何編碼技術。其中有些內容出自個人理解,難免有謬誤,歡迎拍磚。
第一篇就介紹一下最普通的兩個屬性頁內容。
---------------------------------------------------------------------------------------------------------------------
常規:
- 輸出目錄:
項目生成最終文件的保存位置,用宏和相對路徑來配置,保證工程的可拷貝。
- 中間目錄:
項目編譯生成臨時文件(.obj等)所保存的位置。
- 清除時要刪除的擴展名:
刪除項目生成時的符號表文件、Obj文件等中間文件和輸出文件。
- 生成日志文件:
更詳細的項目編譯鏈接信息,包括命令行執行情況、輸出情況和最終結果。
- 繼承的項目屬性表:
當一個解決方案中有多個項目,並且項目互相有多個相同的屬性(比如附加包含目錄、附加庫目錄等),當某一附加目錄的名稱或位置發生變化時,需要重新修改多個項目的相關屬性。使用繼承的項目屬性表,可以將多個工程的屬性配置信息單獨提出成一個配置文件,各個項目共享此配置文件。
這樣就解決了上述問題。
- 啟用托管增量生成:
啟用托管增量生成屬性允許您指定是否要使用增量生成。如果沒有增量生成,代碼必須重新編譯每次更改時引用的程序集。出現此現象,甚至當更改進行內在化處理,例如,當您添加的注釋。如果您啟用啟用托管增量生成屬性時,編譯器將確定對程序集的任何更改是否會影響依賴於該程序集的項目。僅當所做的更改會影響它所依賴的項目將被重建。 這個是MSDN上對這個選項的介紹。我做了一些嘗試,企圖發現他們的不同,最后沒有找到。可能是代碼結構比較簡答的緣故吧。
- 配置類型:
會根據配置類型進行一些生成文件類型的配置。比如.exe時,會查找有沒有入口函數,沒有就會報錯等。
MFC的使用:
如果項目是MFC項目,或者其他項目中使用到了MFC庫,可以使用此選項來配置如何處理對MFC庫的依賴關系。
“在共享DLL中使用MFC”————在安裝vc分發包(vc_redist)的系統中,會查找MFC的依賴DLL並加載他們。所以項目生成的文件比較小,但部署就比較麻煩了。
“在靜態庫中使用MFC”————即使在沒有安裝對應版本的分發包的系統中也能正確使用。部署簡單,但生成文件比較大。
上述兩個選項的區別就在於是在鏈接時使用MFC庫(LIB)還是在運行時使用MFC庫(DLL)。
這個選項不是告訴用戶選擇上面兩個選項就可以直接使用MFC了。還需要包含afxwin.h的。
另外這個選項是只適用於MFC的,有的時候即使適用靜態庫,還是會出現“找不到XXXX.dll”的錯誤。這個就和/MT、/MD、/MTd、/MDd選項有關了。這幾個開關的意思,會在以后的文章中介紹。
- ATL的使用:
同“MFC的使用“。
- 字符集:
使用多字節字符集還是Unicode字符集。使用不同字符集,每個字符占多少字節不一樣,更多關於字符集的知識請百度。
我們在使用MessageBox這樣的函數時,MessageBox這個函數名實際上並不是user32.dll的導出函數。user32.dll實際導出的是MessageBoxA和MessageBoxW
這樣的函數。
在winuser.h里有關於MessageBox的這樣的一個宏:
#if defined(_M_CEE)
#undef MessageBox
__inline
int
MessageBox(
HWND hWnd,
LPCTSTR lpText,
LPCTSTR lpCaption,
UINT uType
)
{
#ifdef UNICODE
return MessageBoxW(
#else
return MessageBoxA(
#endif
hWnd,
lpText,
lpCaption,
uType
);
}
#endif /* _M_CEE */
使用Unicode時,實際上是使用MessageBoxW,使用MBCS,使用的是MessageBoxA。其他API、MFC庫函數都類似。
- 公共語言運行時支持:
這個是.net支持的選項。
.net支持的都是托管類代碼。所謂托管類代碼就是項目生成的文件並非是本地代碼,而是一種中間代碼。運行時需要進一步轉換成本地代碼。
- 全程序優化:
不太懂。只知道Debug時不要使用這個選項,否則會跟錯斷點。Release版本使用這個選項,程序執行會效率高點,體積也小點。
調試
這個主要不講調試屬性頁內各個屬性設置的意思,只講講調試本身。“運行->出錯->關閉->下斷點->再運行->命中斷點”,我們平時都在這樣調試。
“其實調試是一門技術,更是一門藝術。學習調試,會讓菜鳥了解系統,從而變得更Geek,更Hack。”我們公司一位大牛說的,大概意思是這樣,具體怎么說的忘了...
不知道大家遇到過這種情況沒:
(1)程序一運行就崩,但下斷點后單步運行后沒有任何問題。
(2)跟蹤windows消息時,對分發函數設斷點,啟動后總會意外的命中,F5繼續,再意外命中。比如跟蹤WM_PAINT?
以上兩種情況,在本機調試是比較麻煩的。因為有時候命中斷點進入調試器會導致線程上下文的切換,一些多線程的問題很難調出來。或者不想在第一次命中斷點時就中斷(可以加命中次數或數據斷點,但命中次數未知,變量又是臨時變量呢?)
那么就用遠程調試吧。
遠程調試時,線程的上下文就比較清晰了,能發現一些不能在本地發現的問題。
F5運行,程序蹦了怎么辦?
先不要急着關閉,嘗試用調試器附加到進程,這樣就能看到崩潰時的堆棧調用等信息。如果有pdb和源碼,就能直接看到在哪個函數的什么位置失敗了。這個方法本地調試和遠程調試都很有用。
遠程調試器很好配置,把remote debug tools拷貝到遠程機,做點配置就可以了。在VS里選擇遠程調試器,再按F5就開始在遠程執行了。調試方法和本地調試一樣。
另外調試不要拘泥在VS里面。WinDbg調試、Log日志分析調試,調試方法有很多很多。
我是軟件開發工程師,又不是測試工程師,為什么要學這么多調試?
測試:發現問題
調試:發現問題,定位問題,明確原因,解決問題。
調試本來就是軟件開發工程師的活兒。
推薦一本外國大牛的書《windows高級調試》