各類不同類型指針的區別到底是什麼呢?
比如:double *、float*、int * 、char *、void *等;它們之間存在着哪些不同呢?
在這裏,針對int *和cha *做個實驗,以便更好的理解。
#include <stdio.h>
int main(void)
{
int *p;
char *q;
int k = 10;
char i = 10;
p = &k;
q = &i;
printf("&p = %p\n",&p);
printf("&q = %p\n",&q);
printf("&k = %p\n",&k);
printf("&i = %p\n",&i);
printf("p-> = %p\n",p);
printf("q-> = %p\n",q);
printf("k-> = %p\n",&k);
printf("i-> = %p\n",&i);
printf("------------------------------------\n");
printf("------------------------------------\n");
p++;
q++;
printf("&p = %p\n",&p);
printf("&q = %p\n",&q);
printf("&k = %p\n",&k);
printf("&i = %p\n",&i);
printf("p-> = %p\n",p);
printf("q-> = %p\n",q);
printf("k-> = %p\n",&k);
printf("i-> = %p\n",&i);
return 0;
}
運行結果:
&p = 0x7ffffc7ba8d8
&q = 0x7ffffc7ba8e0
&k = 0x7ffffc7ba8d4
&i = 0x7ffffc7ba8d3
p-> = 0x7ffffc7ba8d4
q-> = 0x7ffffc7ba8d3
k-> = 0x7ffffc7ba8d4
i-> = 0x7ffffc7ba8d3
------------------------------------
------------------------------------
&p = 0x7ffffc7ba8d8
&q = 0x7ffffc7ba8e0
&k = 0x7ffffc7ba8d4
&i = 0x7ffffc7ba8d3
p-> = 0x7ffffc7ba8d8
q-> = 0x7ffffc7ba8d4
k-> = 0x7ffffc7ba8d4
i-> = 0x7ffffc7ba8d3
首先i和k變量的地址沒有變化。p 、q指針變量本身的地址值也沒有發生變化,但是p++後,指向的地址值由0x7ffffc7ba8d4 變成了0x7ffffc7ba8d8 ,增加了4個字節。q++後,指向的地址值由0x7ffffc7ba8d3變成了0x7ffffc7ba8d4增加了一個字節。
爲什麼會發生這種變化呢?
因爲p是int*,int在此次編譯平臺中佔用4個字節的內存地址,所以p++之後,指針指向的地址偏移了4個字節。
q是char*,佔用一個字節的內存地址,所以q++之後,指針指向的地址偏移了一個字節。同理,double *、float*也類似。
上圖表示中,出現了一個類似的bug問題,q指向的位置怎麼跑到p指向的地址上去了?
個人覺得這不是問題,這就是指針的魅力,指針本身沒有問題,但是如果你要操作指針指向的值,這個時候就會出問題。
嚴格的說,上面的程序並不符合C語言的標準,只是爲了更好的理解,所以纔會那麼操作。
總結:
對於指針的加減運算,標準只允許指針指向數組內的元素,或者超過數組長度的下一個元素。指針運算的結果也只是允許指針指向數組內的元素,以及超過數組長度的下一個元素。
今天沒有說到void *,想聽繼續分解,請見下篇博文。