發表文章

目前顯示的是 3月, 2011的文章

不可思議: for (i = 0; i < 10; i++) 停不下來 !?

圖片
其實這是一個真實事件... 某一天上班時,我從一早就三不五時的聽到坐在我背後的同事低聲的哇哇叫。幾次下來,我也忍不住好奇的湊過去看看到底是怎麼一回事。結果他Demo了這麼一個不可思議的for迴圈給我看,難怪他一整個早上都在哇哇叫。這位同事因為整個陷入在這個不可思議的for迴圈裡而跳不出來,找不到問題的所在。但當局者迷,我當下眉頭一皺發覺事情並不單純,問題肯定不是出在這個for迴圈上面,再怎麼去看也是白癈力氣。這種奇奇怪怪的問題,很有可能是和記憶體的使用有關係,這個不可思議的for迴圈只不過是因為其它地方的Bug,所產生的現象。我把我的想法告訴了我這位同事後,過了不了多久,果然在其它地方找到了真正的問題所在,的確是因為記憶體的使用不當造成的現象。 ; 底下在VC2003寫支小程式,立刻就能摸擬出這樣的現象。 int main() { int i, a[1]; for (i = 0; i < 10; i++) { a[i] = 0; } } 如上所示,我宣告了一個只有一個元素的陣列a,然後用一個for迴圈去填a的內容。這裡所要示範的一個概念是:會產生這樣的問題,是因為i的值被其它人動到了。而在這個簡單的例子,就是利用這個概念,想辨法讓在填a的內容時,因為填寫錯誤(超出範圍),而去覆寫了i的值,而造成for迴圈停不下來的奇妙現象。 如圖在除錯模式中,在Watch裡加上檢視i和陣列a的位址和內容,然後一步步執行看看。可以發現i的位址和a[3]重疊了,但問題是a只宣告了一個元素,而這個迴圈卻打算存取10個元素。在這樣的情況下,i的值果然被覆寫了,所以這個for迴圈就這樣成為無窮迴圈而永遠跳不出來。 ; PS: 這個實驗是在VC2003和2005上作的,在其它Compiler也許會有不一樣的結果。

關於最佳化

過早作最佳化是萬惡的根源 (Premature optimization is the root of all evil.) 最佳化守則 別作! (Don't do it!) 高手專用:先別作! (For experts only: Don't do it yet!)