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

C++ 變數作用域深度解析:為什麼兩個 score 輸出值不同?

     編輯:程式設計綜合問答

程式碼情境

#include <stdio.h>
int main() {
    int a = 20;
    int score;
    {
        a = 10;
        score = a + 250;
        int score = 30;
        printf("%d\n", score);
    }
    printf("%d\n", score);
    return 0;
}

執行結果輸出為:

30
260

初學者常困惑:為什麼第二個輸出是 260 而不是 30? 明明在內層區塊宣告了 int score = 30,外層應該也被影響才對?

核心概念:變數遮蔽與作用域

這是典型的變數遮蔽問題。在 C/C++ 中,內層區塊宣告的同名變數會遮蔽外層區塊的同名變數,兩者是完全獨立的記憶體空間。

記憶體模型圖解

{ // 外層區塊 A
    int score[addr1];  // 生命週期:整個 A 區塊
    ...
    { // 內層區塊 B
        score[addr1] = a + 250;  // 操作外層 score (addr1)
        int score[addr2] = 30;   // 宣告新變數 score (addr2),遮蔽外層
        printf score[addr2];     // 輸出 30 (addr2)
    } // 區塊 B 結束,addr2 釋放
    printf score[addr1];         // 輸出 260 (addr1)
} // 區塊 A 結束

逐步執行流程

  1. 外層宣告 int score (位址 addr1),未初始化
  2. 進入內層區塊,a = 10
  3. score = a + 250 → 外層 score (addr1) 被賦值 260
  4. int score = 30 → 宣告新變數 score (位址 addr2),遮蔽外層
  5. printf 輸出內層 score (addr2) = 30
  6. 內層區塊結束,addr2 釋放,外層 score (addr1) 恢復可見
  7. printf 輸出外層 score (addr1) = 260

除錯建議

若難以理解,可使用 Visual Studio 單步除錯,監控 &score 位址變化:

  • 輸出 30 時,&score 為 addr2
  • 輸出 260 時,&score 為 addr1

最佳實踐

  • 避免在巢狀區塊使用同名變數,造成閱讀困擾
  • 善用編譯器警告(如 -Wshadow)偵測遮蔽問題
  • 變數命名應具語意,減少重名機率

總結

兩個 score 是完全獨立的變數,內層宣告 int score = 30 只是建立新變數遮蔽外層,並不會修改外層變數值。理解作用域規則是 C/C++ 程式設計的基礎關鍵。

  1. 上一篇文章:
  2. 下一篇文章:
Copyright © 程式碼之家 All Rights Reserved