5.1 返回整數的getchar函數

 我們首先考慮下面的例子:

  1. #include <stdio.h> 
  2.  
  3. main() 
  4.  
  5.    char c; 
  6.  
  7.    while((c = getchar()) != EOF) 
  8.  
  9.        putchar(c); 
  10.  } 

  getchar函數在一般情況下返回的是標準輸入文件中的下一個字符,當沒有輸入時返回EOF(一個在頭文件stdio.h中被定義的值,不同於任何一個字符,一般是 -1)。這個程序咋一看似乎是把標準輸入複製到標準輸出,實則不然。

  原因在於程序中的變量c被聲明爲char類型,而不是int類型。這意味着c無法容下所有可能的字符,特別是,可能無法容下EOF。

  註解: 因爲編譯器實現char類型的方式有時是signed char,而有時是unsigned char。

  因此,最終結果存在兩種可能。一種可能是,某些合法的輸入字符在被“截斷”後使得c的取值與EOF相同;另一種可能是,c根本不可能取到EOF這個值。對於前一種情況,程序將在文件複製的中途終止;對於後一種情況,程序將陷入一個死循環。

  註解: 對於第一種可能,本人認爲發生截斷後,不會給程序帶來額外的影響。因爲ASCII碼字符一共就127個,也就是說char類型足以表示了,所以說截斷和不截斷沒有什麼區別,但要顯示的不是ASCII碼錶中的字符,比如中文,就另當別論了;對於第二種情況就是當編譯器實現的char爲unsigned char類型時,會陷入死循環。

  實際上,還可能存在第三種情況: 程序表明上似乎能夠正常工作,但完全是因爲巧合。儘管函數getchar的返回結果在賦給char類型的變量c時會發生“截斷”操作,儘管while語句中比較運算的操作數不是函數getchar的返回值,而是被“截斷”的值c,然而令人驚訝地是許多編譯器對上述表達式的實現並不正確。這些編譯器確實對函數getchar的返回值作了“截斷”處理,並把低端部分賦給了變量c。但是,它們在比較表達式中並不是比較c與EOF,而是比較getchar函數的返回值與EOF!編譯器如果採取的是這種做法,上面的例子程序看上去就能夠“正常”運行了。

發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章