首頁
編程語言
C語言|JAVA編程
Python編程
網頁編程
ASP編程|PHP編程
JSP編程
數據庫
MYSQL數據庫|SqlServer數據庫
Oracle數據庫|DB2數據庫
您现在的位置: 程式碼之家 >> 編程語言 >  >> C語言 >> C >> C 語言問答

C 語言 while((ch=getchar())='0') 為何輸入 1234567890 會印 11 個 #?

     編輯:C 語言問答

錯誤代碼還原

#include <stdio.h>
void main() {
    char ch;
    while ((ch = getchar()) = '0')  // 錯誤:使用 =(賦值)而非 ==(比較)
        printf("#");
}

逐步執行推演

  1. getchar() 讀取輸入緩衝區第一個字元 '1'。
  2. ch = getchar() → ch 變 '1',整個賦值表達式的值也是 '1'(ASCII 49,非零)。
  3. ... = '0' → 將字元常數 '0'(ASCII 48)賦值給左邊的賦值表達式結果。但左邊不是左值(無法寫入),此行代碼在標準 C 中編譯應報錯「lvalue required」。若編譯器勉強通過(某些舊編譯器允許),行為未定義。
  4. 假設條件判斷取「賦值後右值」即 '0'(非零),while 條件恆真 → 無限迴圈印 #,直到緩衝區耗盡讀到 EOF(-1),賦值 ch = EOF,再 = '0',條件仍非零……

正確寫法:比較而非賦值

while ((ch = getchar()) != '0')   // 讀到 '0' 才停止
    printf("#");

或更完整處理 EOF:

int ch; // 用 int 接收 EOF
while ((ch = getchar()) != EOF && ch != '0')
    putchar('#');

為何提問者看到 11 個 #?

輸入 1234567890\n 共 11 個字元(含換行)。若條件寫成 == '0',迴圈會在讀到 '0' 時結束,共執行 10 次(1~9 印 #,0 不印)。但原代碼用 = 導致條件恆真,實際行為取決於編譯器對非法賦值的處理,不可移植、不可預期。

核心教訓

  • 條件判斷永遠用 ==,賦值用 =,寫反是 C/C++ 經典坑。
  • 開啟編譯器警告(-Wall -Wextra -Wparentheses)會提示「suggest parentheses around assignment used as truth value」。
  • getchar() 回傳 int,變數宜宣告為 int 以正確處理 EOF。
  1. 上一篇文章:
  2. 下一篇文章:
Copyright © 程式碼之家 All Rights Reserved