一江春水向東流

          做一個有思想的人,期待與每一位熱愛思考的人交流,您的關(guān)注是對我最大的支持。

            BlogJava :: 首頁 :: 新隨筆 :: 聯(lián)系 :: 聚合  :: 管理 ::
            44 隨筆 :: 139 文章 :: 81 評論 :: 0 Trackbacks
          看似簡單的一段程序如下:
          ?int main()
          {
          ?? int i,j[8];
          ?? for(i=0;i<=8;i++)
          ??? j[i]=0;
          ?? return 0;
          }?
          ??? gcc編譯運行會陷入死循環(huán).??
          ?
          ??? 因為變量 i 和數(shù)組 j[8]是保存在棧中,默認是由高地址向低地址方向存儲. 輸出變量地址可以發(fā)現(xiàn): i 存儲位置在0xbfd90dec, j[0]、j[1]...j[7]在內(nèi)存的地址分別是0xbfdab05c、0xbfdab060,...0xbfdab078. 如下所示:
          ???????? ?高地址 <--------------------------------------->低地址
          ???????????????????? ?? ? ?i,j[7],j[6],j[5],j[4],j[3],j[2],j[1],j[0]
          ?
          ??? 如果在int i,j[8]后面再定義變量int c,那么c就存放在j[0]的往低方向的下一個地址0xbfdab058 .

          ????? 現(xiàn)在不難理解這段程序為什么會出現(xiàn)死循環(huán)了。j[8]的位置就是變量i所在的位置。這樣當(dāng)i=8時的j[i]=0語句,實際上就是將i的值置為0,然后 i 又從0到8循環(huán)一直下去.? 如果將原句改為int j[8],i; 就不會出現(xiàn)死循環(huán),而僅僅是一個段越界錯誤.

          另一個程序:
          #include <stdio.h>
          int main()
          {
          ??????? int i;
          ??????? char c;
          ??????? for(i=0;i<5;i++)
          ??????? {
          ??????????????? scanf("%d",&c);
          ??????????????? printf("i=%d ",i);
          ??????? }
          ??????? printf("\n");
          }
          編譯后運行
          [foxman@local~]#./a.out
          0??? (輸入0)
          i=0? (輸出 i 值)
          1
          i=0
          2
          i=0
          3
          i=0
          4
          i=0
          ...
          這樣一直循環(huán)下去。

          問題在于,c被聲明為char類型,而不是int類型。當(dāng)程序要求scanf讀入一個整數(shù)時,應(yīng)該傳遞給它一個指向整數(shù)的指針。而程序中scanf得到的卻是一個指向字符的指針,scanf函數(shù)并不能分辨這種情況,只能將這個指向字符的指針作為指向整數(shù)的指針而接受,并且在指針指向的位置存儲一個整數(shù)。因為整數(shù)所占的存儲空間要大于字符所占的存儲空間,所以c附近的內(nèi)存會被覆蓋.

          由上面分析,i 和 c 是由高地址到低地址存儲在棧中,這樣在c所在位置嘗試存儲一個4字節(jié)變量,會占用比c高的3個字節(jié)(覆蓋掉 i 字節(jié)的低3位),即使 i 總是為零,一直循環(huán)下去.

          如果每次輸入Ctrl+D作為字符終止符不存儲int到c處,那么就會輸出正常i=0..4了.

          posted on 2007-12-25 18:18 allic 閱讀(545) 評論(0)  編輯  收藏 所屬分類: C/C++
          主站蜘蛛池模板: 青海省| 晋州市| 东安县| 彭阳县| 锡林郭勒盟| 遂川县| 集安市| 安龙县| 呼图壁县| 诸暨市| 海丰县| 历史| 宽甸| 水富县| 文山县| 邵阳县| 利津县| 安庆市| 新绛县| 岗巴县| 神农架林区| 吉隆县| 清远市| 木兰县| 达孜县| 建始县| 奈曼旗| 左云县| 金堂县| 东港市| 安顺市| 沈阳市| 清丰县| 江西省| 库尔勒市| 梅河口市| 青岛市| 郧西县| 清新县| 南雄市| 嘉黎县|