許多程序員喜歡抱怨編譯器報出的各做錯誤,難道真的是編譯器問題嗎?下面就讓我們來談談吧!
你確定嗎?
當程序員告訴你,編譯器會產生錯誤,請問你會信嗎?99%的情況下,你會把它當作一個謊言或者是笑話,甚至在內心會嘲笑這個程序員。
通常編譯報的錯主要有以下幾種:
- 數組溢出
- 變量沒有初始化
- 輸出錯誤
- 同步錯誤
- 非法使用變量
- 調用未定義方法或其它
- 等等
對編譯器報出的這些錯誤你是否早已如數家珍,但這并沒有阻止程序員一次次對編譯器的指責與抱怨。似乎這一切都是編譯器的錯!
編譯器也可能包含錯誤,但是這種機率真的很小,除非你使用一些稀奇古怪的編譯器。在我多年使用Visual C++的職業生涯中,我只看到一次匯編代碼生成錯誤。
建議
當你在開始抱怨前,首先檢查一下自己的代碼是否有錯并且已更正,其次,最好看看別的程序員是如何評價這個錯誤的。
目的
先奉上一段編譯代碼供大家娛樂一下:
- TprintPrefs::TprintPrefs(IffdshowBase?*Ideci, ?
- ?????????????????????????const?TfontSettings?*IfontSettings) ?
- { ?
- ??memset(this,?0,?sizeof(this));?//?This?doesn't?seem?to ?
- ?????????????????????????????????//?help?after?optimization. ?
- ??dx?=?dy?=?0; ?
- ??isOSD?=?false; ?
- ??xpos?=?ypos?=?0; ?
- ??align?=?0; ?
- ??linespacing?=?0; ?
- ??sizeDx?=?0; ?
- ??sizeDy?=?0; ?
- ??... ?
- }?
我可以想象程序員看到這段注釋會有多憤怒,多令人討厭的編譯器!在調試版本階段,所有變量都被賦0值。由于優化問題,在發布版本中會包含一些垃圾。面對這種情況,最好的解決之道便是檢查代碼,而作為程序員,你還需繼續編寫代碼,用勇氣戰勝邪惡!
下面讓我們來分析上面這段代碼,你發現沒?memset()函數不工作的原因僅僅是因為一個非常簡單的錯誤:第三個參數是計算指針的大小而不是計算結果的尺寸。正確的調用應該是:“memset(this,0,sizeof(*this));”
順便說一句,函數memcpy()函數的效率也非常低。我確信,程序員肯定會說編譯器開發商真迂腐。
- void?Assign(const?AVSValue*?src,?bool?init)?{ ?
- ??if?(src->IsClip()?&&?src->clip) ?
- ????src->clip->AddRef(); ?
- ??if?(!init?&&?IsClip()?&&?clip) ?
- ????clip->Release(); ?
- ??//?make?sure?this?copies?the?whole?struct! ?
- ??//((__int32*)this)[0]?=?((__int32*)src)[0]; ?
- ??//((__int32*)this)[1]?=?((__int32*)src)[1]; ?
- ??memcpy(this,src,sizeof(this)); ?
- }?
從注釋中可以明白這段代碼試圖從其他方法中拷貝內存。然而,編寫這段代碼的程序員試圖丟棄使用memcpy()方法。當程序員想要復制的結構體正好是8字節的時候,在64位系統里面正好可以運行。
通過上面的分析大家可以明白,抱怨與指責編譯器(制造商)是無法解決任何問題的,只會浪費時間,無法靜下心繼續編寫代碼。還是好好 檢查一下你們自己的代碼吧!此外,工具是死的,人是活的,程序員們,你們才是 工具的主人!