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

C語言進階核心知識點:數組參數退化、指針算術、32/64位差異

     編輯:C 語言入門

1. 數組作為函數參數:退化為指針

數組傳給函數時傳遞的是首元素地址,而非整個數組。以下聲明等價:

void sortArray(int a[], int num);
void sortArray(int a[100], int num);
void sortArray(int *a, int num);  // 本質

冒泡排序實現:

void sortArray(int *a, int num) {
    int i, j, temp;
    for(i=0; i a[j]) { temp=a[i]; a[i]=a[j]; a[j]=temp; }
}

2. 參數傳遞陷阱:sizeof 失效

實參為數組名時 sizeof(a) 返回整個數組字節數;但形參接收為指針後,sizeof(p) 僅得指針大小。

int a[] = {1,3,5,...};  // 32字節
int num = sizeof(a)/sizeof(a[0]);  // 正確得 8

int test=5; int *p=&test;
int num1 = sizeof(p)/sizeof(p[0]);  // 錯誤!等價 sizeof(int*)/sizeof(int)
// 32位:4/4=1 正確;64位:8/4=2 錯誤!

結論:函數內無法通過 sizeof 計算數組長度,必須額外傳遞長度參數。

3. 數組參數聲明的四種等價形式

// 原型聲明(可省略參數名)
int sum(int *a, int n);
int sum(int *, int);
int sum(int a[], int n);
int sum(int [], int);

// 函數定義(不可省略名)
int sum(int *a, int n) { ... }
int sum(int a[], int n) { ... }

4. a 與 &a 的本質區別

int a[] = {1,3,5,12,6,7,54,32};
printf("a:%p, a+1:%p, &a:%p, &a+1:%p\n", a, a+1, &a, &a+1);

輸出示例(地址假設):

a:0x190000, a+1:0x190004, &a:0x190000, &a+1:0x190020
  • a:首元素地址(int*),a+1 增加 sizeof(int)。
  • &a:整個數組地址(int(*)[8]),&a+1 增加 sizeof(int[8]) = 32 字節。
  • 雖然數值相同,但類型不同,指針算術步長不同。

5. 指針大小與 32/64 位差異

指針大小由操作系統/編譯器決定:

  • 32 位:所有指針 4 字節
  • 64 位:所有指針 8 字節

驗證代碼:

printf("sizeof(int*):%zu sizeof(double*):%zu sizeof(char*):%zu\n",
       sizeof(int*), sizeof(double*), sizeof(char*));

這直接導致 sizeof(p)/sizeof(p[0]) 在 64 位下得 2 而非 1,引發邏輯錯誤。

6. 實參數組類型的特殊性

調用時 sizeof(a) 為整個數組字節數(32),說明實參 a 在此上下文類型為數組類型,而非指針。但傳遞給函數時發生隱式轉換為指針。

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