指针数组、数组指针、数组的区别与联系
? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ?指針數(shù)組、數(shù)組指針、數(shù)組的區(qū)別與聯(lián)系!
一:基本定義
1.指針數(shù)組
char *arr[4] = {"hello", "world", "shannxi", "xian"};
//arr就是我定義的一個(gè)指針數(shù)組,它有四個(gè)元素,每個(gè)元素是一個(gè)char *類(lèi)型的指針,這些指針存放著其對(duì)應(yīng)字符串的首地址。
(1)這個(gè)指針數(shù)組有多大呢?答案是16個(gè)字節(jié),因?yàn)樗且粋€(gè)指針數(shù)組。(這是廢話,正話下面說(shuō)) 每當(dāng)出現(xiàn)這些問(wèn)題時(shí),腦子里一定要第一時(shí)間反應(yīng)出內(nèi)存映像圖如下:
這里最左側(cè)一列是一個(gè)很簡(jiǎn)陋但能說(shuō)明意思的內(nèi)存圖,一般情況下,從棧區(qū)到代碼區(qū),是從高地址到低地址。棧向下增長(zhǎng),堆向上增長(zhǎng)。
(2)arr[4]是一個(gè)在主函數(shù)定義的數(shù)組。把它對(duì)應(yīng)到對(duì)應(yīng)到內(nèi)存中,arr是一個(gè)在棧區(qū),有四個(gè)元素的數(shù)組,而每一個(gè)數(shù)組又是一個(gè)指針,所以說(shuō)它的四個(gè)元素各占四個(gè)字節(jié),所以變量arr的大小是16個(gè)字節(jié)。
那么就有人問(wèn)了?初始化arr的{“hello”, “world”, “shannxi”, “xian”};的是什么鬼??
這四個(gè)不是什么鬼,他們也存在在內(nèi)存中,只是跟arr這個(gè)變量不在同一段空間,它們被分配在只讀數(shù)據(jù)區(qū),數(shù)組arr[4]的四個(gè)指針元素,分別存放著這四個(gè)字符串的首地址,想象一下,從棧區(qū)有四只無(wú)形的手指向數(shù)據(jù)區(qū)的空間。arr+1會(huì)跳過(guò)四個(gè)字節(jié),。也就是一個(gè)指針的大小 ,這就相當(dāng)與定義char *p1 = “hello”,char *p1 = “world”,char *p3 = “shannxi”, char *p4 = “xian”,這是四個(gè)指針,每個(gè)指針存放一個(gè)字符串首地址,然后用arr[4]這個(gè)數(shù)組分別存放這四個(gè)指針,就形成了指針數(shù)組。
2.數(shù)組指針
首先來(lái)定義一個(gè)數(shù)組指針,既然是指針,名字就叫pa。
char (*pa)[4];
(1)char *pa[4]和char (*pa)[4],原來(lái)指針數(shù)組和數(shù)組指針的形成的根本原因就是運(yùn)算符的優(yōu)先級(jí)問(wèn)題.
(2)pa是一個(gè)指針指向一個(gè)char [4]的數(shù)組,每個(gè)數(shù)組元素是一個(gè)char類(lèi)型的變量,所以我們不妨可以寫(xiě)成:char[4] (*pa);這樣就可以直觀的看出pa的指向的類(lèi)型,不過(guò)在編輯器中不要這么寫(xiě),因?yàn)榫幾g器根本不認(rèn)識(shí),這樣寫(xiě)只是幫助我們理解。
(3)既然pa是一個(gè)指針,存放一個(gè)數(shù)組的地址,那么在我們定義一個(gè)數(shù)組時(shí),數(shù)組名稱(chēng)就是這個(gè)數(shù)組的首地址,那么這二者有什么區(qū)別和聯(lián)系呢?
char a[4];
a是一個(gè)長(zhǎng)度為4的字符數(shù)組,a是這個(gè)數(shù)組的首元素首地址。既然a是地址,pa是指向數(shù)組的指針,那么能將a賦值給pa嗎?答案是不行的!因?yàn)閍是數(shù)組首元素首地址,pa存放的卻是數(shù)組首地址,a是char 類(lèi)型,a+1,a的值會(huì)實(shí)實(shí)在在的加1,而pa是char[4]類(lèi)型的,pa+1,pa則會(huì)加4,雖然數(shù)組的首地址和首元素首地址的值相同,但是兩者操作不同,所以類(lèi)型不匹配不能直接賦值,但是可以這樣:pa = &a,pa相當(dāng)與二維數(shù)組的行指針,現(xiàn)在它指向a[4]的地址。
二:指針數(shù)組和數(shù)組指針的使用
1.指針數(shù)組的應(yīng)用
(1)指針數(shù)組在參數(shù)傳遞時(shí)的使用
指針數(shù)組常用在主函數(shù)傳參,在寫(xiě)主函數(shù)時(shí),參數(shù)有兩個(gè),一個(gè)確定參數(shù)個(gè)數(shù),一個(gè)這是指針數(shù)組用來(lái)接收每個(gè)參數(shù)(字符串)的地址.
int main(int argc, char *argv[])
此時(shí)可以想象內(nèi)存映像圖,主函數(shù)的棧區(qū)有一個(gè)叫argv的數(shù)組,這個(gè)數(shù)組的元素是你輸入的參數(shù)的地址,指向著只讀數(shù)據(jù)區(qū)。
如果是向子函數(shù)傳參,這和傳遞一個(gè)普通數(shù)組的思想一樣,不能傳遞整個(gè)數(shù)組過(guò)去,如果數(shù)組很大,這樣內(nèi)存利用率很低,所以應(yīng)該傳遞數(shù)組的首地址,用一個(gè)指針接收這個(gè)地址。因此,指針數(shù)組對(duì)應(yīng)著二級(jí)指針。
void fun(char **pp);//子函數(shù)中的形參
fun(char *p[]);//主函數(shù)中的實(shí)參(2)指針數(shù)組的排序
指針數(shù)組的排序非常有趣,因?yàn)檫@個(gè)數(shù)組中存放的是指針,通過(guò)比較指針指向的空間的大小,排序這些空間的地址。函數(shù)實(shí)現(xiàn)如下:
在函數(shù)中定義指針數(shù)組,并且打印結(jié)果如下:
char *pa[4] = {"abc", "xyz", "opq", "xyz"};
[root@menwen-linux test]# ./test?
abc
ijk
opq
xyz
2.數(shù)組指針傳參時(shí)的使用
數(shù)組指針既然是一個(gè)指針,那么就是用來(lái)接收地址,在傳參時(shí)就接收數(shù)組的地址,所以數(shù)組指針對(duì)應(yīng)的是二維數(shù)組。
void fun(int (*P)[4]);//子函數(shù)中的形參,指針數(shù)組?
a[3][4] = {0};//主函數(shù)中定義的二維數(shù)組
fun(a);//主函數(shù)調(diào)用子函數(shù)的實(shí)參,是二維數(shù)組的首元素首地址
?
總結(jié)
以上是生活随笔為你收集整理的指针数组、数组指针、数组的区别与联系的全部?jī)?nèi)容,希望文章能夠幫你解決所遇到的問(wèn)題。
- 上一篇: 进程、线程、堆、栈的理解和区别!
- 下一篇: 静态链接库与动态链接库的优缺点