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

C語言指針算術經典題:字符串長度計算與指針減法原理

     編輯:C 語言問答

題目還原

int fun(char *s) {
    char *p = s;
    while (*p != 0) p++;
    return p - s;
}

// 調用:fun("0ABCDEF") 返回 7

核心誤區分析

題主錯誤理解:

  1. char *p = s; → p指向字符'0' (ASCII 48)
  2. *p 等於字符'0',而非數值0
  3. while(*p != 0) 比較的是字符值與數值0,即'0' != 0 (48 != 0) 為真
  4. 循環直到遇到字符串結束符\0 (數值0) 才停止

內存圖解

地址:     0x1000  0x1001  0x1002  0x1003  0x1004  0x1005  0x1006  0x1007
內容:      '0'     'A'     'B'     'C'     'D'     'E'     'F'     '\0'
           ↑                                               ↑
           s                                               p (循環結束時)
           
p - s = 0x1007 - 0x1000 = 7 (指針差值 = 元素個數 = 字符串長度)

逐步執行追蹤

步驟p地址*p值*p != 0動作
初始0x1000'0'(48)truep++
10x1001'A'(65)truep++
20x1002'B'(66)truep++
30x1003'C'(67)truep++
40x1004'D'(68)truep++
50x1005'E'(69)truep++
60x1006'F'(70)truep++
70x1007'\0'(0)false退出循環

指針減法規則

  • 同一數組內兩指針相減,結果類型為ptrdiff_t (有符號整數)
  • 結果值 = 元素個數差,而非字節差
  • p - s = 7 表示p比s向後7個char元素
  • 等價於(char*)p - (char*)s / sizeof(char)

等價標準庫函數

size_t strlen(const char *s) {
    const char *p = s;
    while (*p) p++;
    return p - s;
}

常見變體與陷阱

1. 指向不同數組的指針相減 → UB

char a[10], b[10];
char *p1 = a, *p2 = b;
ptrdiff_t diff = p1 - p2;  // 未定義行為!

2. 字符'0' vs 數值0 vs 空指針NULL

'0'  = 48 (ASCII)
0    = 0  (整數字面量,也用作空指針常量)
'\0' = 0  (字符字面量,字符串結束符)
NULL = (void*)0  (空指針宏)

3. 指針算術應用:字符串反轉

void reverse(char *s) {
    char *p = s;
    while (*p) p++;  // p 指向 \0
    p--;             // 指向最後一個字符
    while (s < p) {
        char tmp = *s;
        *s++ = *p;
        *p-- = tmp;
    }
}

考試重點總結

  1. 指針遍歷字符串:while(*p) 或 while(*p != '\0')
  2. 指針減法得長度:p - s 等價於 strlen(s)
  3. 字符'0'非數值0:ASCII 48,作為條件判斷為真
  4. 字符串結束符\0:數值0,作為條件判斷為假
  5. 指針差值類型:ptrdiff_t (通常在中定義)

這道題考察指針算術、字符串內存佈局、字符與數值區別三大核心知識點。畫內存圖、逐步追蹤是解決此類問題的最有效方法。

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