這周開始作C語言筆試卷,什麼嘛!考的都是概念,各類細節,雖然貌似書上都能找到,但我還真不清楚...頓時又有一種我C語言學的好渣的感受 T_T數組
好了,說下在【上機實驗藍皮書背後,綜合測試題二】中難到的2道題,這兩道題使得你對【指針數組】和【數組指針】的區別更加清晰。函數
【例題1】測試
有如下程序:spa
1 #include <stdio.h> 2 3 int main() 4 { 5 char *s[] = {"one", "two", "three"}, *p; 6 p = s[1]; 7 printf("%c, %s\n",*(p+1), s[0]); 8 return 0; 9 }
執行後的結果是_______。指針
A. n, two B. w, one C. t, one D. o, twocode
第一次我選了 C,由於我覺得 (p+1) 是指向 "three「 的。這是對指針 p 類型的理解錯誤。blog
正確答案是 B,由於: three
1 #include <stdio.h> 2 3 int main() 4 { 5 char *s[] = {"one", "two", "three"}; // s是一個指針數組,元素是3 6 // 個指向字符串常量的指針 7 char *p = s[1]; // p是一個指向字符串的指針變量 8 printf("%c, %s\n",*(p+1), s[0]); 9 // (p+1)是p的地址加一個字符內存的大小,從指向t變成指向w 10 return 0; 11 }
因此,平時咱們說的指向字符串的指針,其實都是指向一個字符,因此對它進行位移運算時,加減都是1。
另外,若是你把第8行內存
printf("%c, %s\n",*(p+1), s[0]);
改爲 字符串
printf("%c, %s\n",*(p+1), s[0]);
輸出就會是:wo,one
【例題2】
1 #include <stdio.h> 2 3 int main() 4 { 5 int a[3][4] = {{1,2,3,4}, {5,6,7,8}, {9,10,11,12}}; 6 int (*p)[4] = a; 7 printf("%d\n", *(*(p+1)+3)); 8 return 0; 9 }
以上代碼執行的結果是_______。
答案是 8
這道題初看我徹底不理解...怎麼*了還能*,(*p)[4]又是什麼鬼...我作這份卷子前把【指針數組】和【數組指針】搞亂了=
是這樣的:
1.(*p)[4]:聲明p是一個指向(4個int元素的數組)的指針,所以 p+1 從指向 a[0],變成指向 a[1]
2.*(*(p+1)+3):爲何會有兩個星?
*(p+1) => a[1][0](也就是5),第一星從a[1]變成a[1][0],這個過程雖然地址沒有變,但指針的類型變了!原來指針+1是加4個 int,如今指針+1只加一個 int 了!!
*(p+1)+3 => a[1][3](也就是8),再取一個*就是從地址裏讀出8
還能夠修改一下原來的代碼弄清楚:
1 #include <stdio.h> 2 3 int main() 4 { 5 int a[3][4] = {{1,2,3,4}, {5,6,7,8}, {9,10,11,12}}; 6 int (*p)[4] = a; 7 printf("p: %p\n",p); 8 printf("p+1: %p\n",p+1); 9 printf("*(p+1): %p\n",*(p+1)); 10 printf("*(p+1)+3: %p\n",*(p+1)+3); 11 printf("%d\n",*(*(p+1)+3)); 12 return 0; 13 }
輸出的結果是:
p: 0x7fff9f4ba180 p+1: 0x7fff9f4ba190 *(p+1): 0x7fff9f4ba190 *(p+1)+3: 0x7fff9f4ba19c 8
好啦~