C指針詳細講解(幫助理解)

指針,是一種數據類型,是用來存儲地址的數據類型。

我們可以通過定義指針變量,然後給這個指針變量中存儲地址,然後再通過指針來訪問這個地址所對應的內容。

上面的是指針的基本感念,幾乎所有的C語言學習者都會在書籍中看到這樣的概念,但是並不會詳細講解指針應該如何進行理解。我個人對指針變量的理解是:指針,通過名字可以理解爲一根針,這根針指向一個內存地址,將這個內存地址存儲在一個指針變量中,在需要用的時候,通過對這塊內存地址中內容的訪問,來拿到所需要的東西。

#include<stdio.h>

int main()
{
    int *p = "hehe";
	
    int *pp = NULL;
    pp = "hello word";
	
    return 0;
}

記住,在定義指針類型的時候,一定要對指針內容進行初始化。如果沒有對指針內容進行初始化,那麼這個指針變量中所存儲的就是一個隨機值,這個指針所指向一塊垃圾地址,這個指針就是一個野指針。如果對這個指針所指向的內容進行訪問,就會發生錯誤。而且如果不小心對這塊內存地址的內容進行修改,就會發生難以預料的結果。因爲在計算機運行的過程中,有很多東西在內存中運行,如果突然對這塊內存地址的內容進行修改,就可能會打斷其中的一個程序的正常運行,會導致非常嚴重的錯誤。如果定義的時候指針沒有指向一個明確的地址,那麼就在定義的時候,讓指針指向空地址,即NULL,NULL的值就是0,pp就是一個空指針。由於計算機會對內存地址爲0的位置進行硬件保護,所以不能進行內容的訪問,也不能進行修改。然後在需要的時候,對這個指針變量進行賦值,讓它指向一塊合法的內存地址。

NULL是一個宏定義,是0。

好了,這就是基本的概念了,那麼我們來看看指針數組、數組指針、指針函數、函數指針、等等很多很多讓人頭皮發麻的東西。其實那些複雜的類型,只不過是一個個簡單的類型拼接起來的,當你看到的時候,一定要冷靜分析,越是冷靜,看到的東西就越多。    

首先,我們來看看運算符的優先級,在指針這裏最重要的就是運算符的優先級,只有明白了優先級,纔會理解爲什麼會出現各種各樣的類型。

* 和 [ ] 和 ( ) ,這三個運算符,因爲優先級的不同,導致了指針的多種變化。( ) 這個運算符的優先級是最高的,不論何時,一定是先對他修飾的進行處理。[ ]的優先級是高於*的優先級的,所有但他們兩個同時出現的時候,計算機會優先進行 [ ] 處理(我不知道具體的用詞應該是什麼),比如   int* p[2]  這個的意思是定義一個有兩個元素的數組,每個元素是一個指針。因爲計算機優先對[]進行了處理,所以計算機首先認爲這是一個數組,然後再對*進行處理,這裏就有一個先入爲主的概念了,因爲計算機已經確定了p是一個數組,那麼既然是一個數組了,那麼數組就是p的主,而 * 及指針則是次,那麼計算機就會認爲這個數組的元素是指針類型。這裏還有一個重要的概念 :在指針和數組混合起來應用的時候,會有一個逐級向內的特性。意思就是一個數組,他是主體,而他的次就是他存儲的元素,而他的元素又是他的元素的元素的次,依次相對爲主次。這麼說可以理解嗎?如果不能,那我們就來看例子 :a->b->c->d  ,看,a是b的老大,b時c的老大,c是d的老大,[ ]和* 運算符在運算的時候,會遵循這個原則,逐級向內訪問, 訪問的等級也會越來越低。

這樣就差不多可以理解了吧!其實這個只要你看的例題多了,就自然而然就會了。話不多說,咋們直接上例子:

int *p1[10];
int (*p2)[10];

這兩個例子,一個是指針數組,一個是數組指針。命名規則是將等級高的放在後面。p1是一個數組,數組元素是指針類型。p2是一個指針,這個指針所指向的類型是一個有是十個元素的數組類型。能看懂這個例子吧?如果如果看不懂,記得一定要注意優先級,因爲訪問的優先級是突破的關鍵。

接下來咋們來看看函數指針和指針函數:

函數指針:函數指針是一個指針,這個指針指向一個函數,這個函數含有多個參數。

指針函數:指針函數是一個函數,函數的返回值是一個指針。

那麼我們接下來加入函數指針,和指針函數試試看你還能不能理解:

其實這不過是一個反覆的運算符訪問。下面的第一個例子是:這是一個指針,指針指向一個參數是char* 類型的指針,返回值是int*類型指針的函數。  第二個例子是:這是一個數組,這個數組的每個元素是一個指針,指針指向一個參數是char* 類型的指針,返回值是char*類型指針的函數。看的時候,一定是從最中心的位置開始,然後逐一分析,就可以得出最終的答案。這裏的中心就是我們上面講到的數組指針和指針數組,從這裏開始看,然後在最後將函數指針和指針函數加進去就可以了。

int *(*pf)(char * p);
char*(*pf[3])(char *p);//這兩個例子出自《C語言深度剖析》

 

 

 

 

 

 

 

 

 

 

 

 

 

 

發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章