在 C 語言學習中,char* const p 這類聲明常讓初學者困惑。有位開發者發現:使用 char* const p 定義字符串時,printf("%s\n", p) 無法正常顯示,甚至將 %s 改為 %c 也無法輸出。這究竟是怎麼回事?
char* const p 表示 p 是一個常量指針,即指針本身的值(地址)不能修改,但它指向的內容可以修改。這與 const char* p(指向常量的指針)有本質區別。
%c:期望對應 char 類型參數,輸出單個字符。%s:期望對應 char* 類型參數,即指向字符串首字符的指針,輸出從該地址開始直到遇到 '\0' 的所有字符。關鍵在於 初始化。char* const p 必須在聲明時初始化,且之後無法改變指向。若寫成:
char* const p; // 錯誤:常量指針未初始化
p = "hello"; // 編譯錯誤:無法修改常量指針
正確寫法:
char* const p = "hello"; // 初始化指向字符串常量區
printf("%s\n", p); // 正常輸出 "hello"
若未初始化,p 存儲的是垃圾地址,導致 %s 讀取非法內存而無輸出或崩潰;%c 則會嘗試將該垃圾地址作為字符輸出,同樣異常。
char* const p 只能存單字符:實際上它完全可以指向字符串,關鍵在於正確初始化。%c 和 %s 的參數類型:%c 要 char,%s 要 char*,傳指針給 %c 是類型不匹配。const char* p = "...",語義更清晰(內容不可改)。char* const p = buffer 指向可修改的緩衝區。理解指針常量與常量指針的區別,配合正確的初始化和格式符,即可避開這類坑。