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

C語言 const 關鍵字完全解析:指標常量 vs 常量指標

     編輯:C 語言入門

const 與指標的四種組合:語法、語意、記憶口訣、實戰陷阱

搞懂 const 與 * 的相對位置,掌握「從右向左讀」口訣,避免面試與實戰中的常見錯誤。

四種核心形式

宣告俗稱指標可改指向值可改口訣 (右→左)
const int *p
int const *p
指標常量
(Pointer to const)
✅❌p is a pointer to const int
int *const p常量指標
(Const pointer)
❌✅p is a const pointer to int
const int *const p雙重常量❌❌p is a const pointer to const int
int *p普通指標✅✅p is a pointer to int

「從右向左讀」口訣詳解

// 步驟:找出變數名,然後向左讀
const int *p;
//       ↑ p 是變數名
//     ← *  : pointer to (指向...)
//   ← int  : int
// ← const  : const (修飾 int)
// 結論:p is a pointer to const int

int *const p;
//       ↑ p
//     ← const : const (修飾 pointer)
//   ← *      : pointer to
// ← int      : int
// 結論:p is a const pointer to int

完整測試程式

#include 

void test_const_pointer() {
    int a = 10, b = 20;
    const int *p = &a; // 指標常量:指向常數的指標
    
    printf("*p = %d\n", *p); // 10
    p = &b;                 // ✅ 可改變指向
    printf("*p = %d\n", *p); // 20
    // *p = 30;            // ❌ 編譯錯誤:不能修改指向的值
}

void test_pointer_const() {
    int a = 10, b = 20;
    int *const p = &a; // 常量指標:指標本身是常數
    
    printf("*p = %d\n", *p); // 10
    *p = 30;                 // ✅ 可修改指向的值
    printf("*p = %d\n", *p); // 30
    // p = &b;              // ❌ 編譯錯誤:不能改變指向
}

void test_const_pointer_const() {
    int a = 10;
    const int *const p = &a; // 雙重常量
    
    printf("*p = %d\n", *p); // 10
    // *p = 20; // ❌
    // p = &b;  // ❌
}

int main() {
    test_const_pointer();
    test_pointer_const();
    test_const_pointer_const();
    return 0;
}

函數參數中的 const

// 1. 不修改指向內容 (唯讀輸入)
void printArray(const int *arr, int n) {
    for (int i = 0; i < n; i++) printf("%d ", arr[i]);
}

// 2. 不修改指向關係 (輸出參數常用)
void setPointer(int *const ptr, int value) {
    *ptr = value; // 修改值 OK
    // ptr = ...; // ❌ 不能改 ptr 本身
}

// 3. 完全不可修改
void safeFunc(const int *const ptr) {
    // 既不改值,也不改指向
}

陣列與 const

const int arr[5] = {1,2,3,4,5};
// arr 退化為 const int* (指標常量)
// arr = other_arr; // ❌ 陣列名不可修改
// arr[0] = 10;     // ❌ 內容不可修改

int *const ptr = arr; // ❌ 編譯警告:丟棄 const
const int *ptr2 = arr; // ✅ 正確

常見面試陷阱

  1. char *str = "literal"; → 字串字面值在唯讀區,應寫 const char *str
  2. const int *p = &a; p = &b; → 合法,指向常數的指標可改向
  3. int *const p = &a; *p = 20; → 合法,常數指標可改值
  4. const 參數傳遞:void f(const int *p) 可接收 int* 或 const int*,反之不行

現代 C++ 延伸

  • constexpr:編譯期常數
  • constinit (C++20):靜態儲存期變數編譯期初始化
  • std::as_const(obj) (C++17):獲得 const 引用
  • 成員函數 const:void foo() const 不修改 this 指向物件
  1. 上一篇文章:
  2. 下一篇文章:
Copyright © 程式碼之家 All Rights Reserved