黑馬程式設計師 C語言指標與陣列

2021-07-02 00:07:38 字數 3399 閱讀 7374

1、指標與位址

一元運算子&用於取乙個物件的位址,因而語句

p = &c;

用於將c的位址賦給變數p,並且說p是指向c的指標。

一元運算子* 是間接定址或間接引用運算子,當它應用於指標時,它將訪問指標所指向的物件。

由於指標也是變數,所以在程式中不必通過間接引用的方法就可以直接使用它們。

例如,如果i q是另乙個指向整數的指標,那麼語句

iq = ip

就將i p的值賦給i q,因此該語句使得指標i q指向i p所指向的物件。

2、指標與函式變元

由於c語言以按值呼叫的方式將變元傳遞給函式,因而被呼叫函式不能直接更改呼叫函式中

變數的值。

定義void swap(int * px, int * py);

呼叫swap(&a, &b);

3、指標與陣列

int *pa;

賦值語句

pa = &a[0]

用於將指標pa指向陣列a的第0個元素,也即pa的值為陣列元素a [ 0 ]的位址

則賦值語句

x = *pa;

把陣列元素a[0]的內容賦給變數x。

下標和指標運算有著很密切的對應關係。按照定義,乙個型別為陣列的變數或表示式的值是該陣列第0個元素的位址。因此在賦值語句

pa = &a[0];

執行後, pa和a具有相同的值。由於乙個陣列的名字即該陣列第0個元素的位置,所以賦值語句

pa = &a[0]也可以寫成如下形式:

pa = a;

乙個用陣列和下標實現的表示式可等價地用指標和和偏移量來實現。然而,必須注意到,陣列名字和指標之間仍然存在著一點區別。指標是變數,因而在c語言中,語句pa = a和p a + +都是合法的。但陣列名字不是變數,因而諸如a = pa和a + +這樣的語句是非法的。

當把乙個陣列名字傳遞給乙個函式時,實際上傳遞的是該陣列第乙個元素的位置。由於乙個陣列名字引數就是乙個指標,所以在被呼叫函式中,與陣列名字引數對應的變元是乙個包含位址值的區域性變數。

在函式定義中,將

char s[ ];  和  char *s;

作為函式的形式引數所表示的含義是等價的,我們更喜歡使用後一種形式,因為它比前者更明白地表示了該引數是乙個指標。當陣列名字被傳遞給函式時,函式就根據操作的方便來判定傳遞給它的是陣列還是指標,然後按相應的方式操縱該引數。為了清楚而恰當地描述函式,在函式中甚至可同時使用陣列和指標這兩種表示法。

也可以通過傳遞指向子陣列的指標的方法把陣列的一部分作為引數傳遞給函式。

4、位址算術運算

指標的算術運算具有一致性:如果處理的是比字元型別佔據更多儲存空間的浮點型別,並且p是乙個指向浮點型別的指標,那麼執行p + +後p就指向下乙個浮點數的位址。因此只需將a l l o c和a f r e e函式中所有的c h a r型別替換為f l o a t型別,就可以得到乙個針對浮點型別而不是字元型別的記憶體分配函式版本。所有的指標運算都會自動考慮它所指物件的大小。

有效的指標運算包括:相同型別指標之間的賦值運算;指標值加或減乙個整數值的運算;指向相同陣列中的元素的指標之間的減或比較運算;將指標賦0或指標與0之間的比較運算。所有其他形式的指標運算均非法。諸如下列形式的運算就是非法的指標運算:指標間的加法、乘法、除法、移位或遮蔽運算;指標值加單雙精度浮點數的運算;除兩者之一是v o i d *型別指標外,不經強制型別轉換就將指向一種型別物件的指標賦給指向另一種型別物件的指標的運算。

5、字元指標與函式

c語言沒有提供將乙個完整的字串作為乙個整體處理的運算子。

如下兩個定義的差別很大:

char amessage[ ] = "now is the time";

char *pmessage = "now is the time";

上述說明中,amessage是乙個足以存放字串初值和空字元'/0' 的一維陣列。可以更改陣列中的單個字元,但amessage是乙個不可改變的常量,它總指向同一儲存區。另一方面, pmessage是乙個指標,其初值指向乙個字串常量,之後它可以被修改指向其他位址,但如果試圖修改字串的內容,結果將不確定。

定義函式使用指標引數時可以有兩個版本的寫法,一是利用陣列下標,一時使用指標移動。

標頭檔案< string.h >中包含本節中所提到的函式的說明,其中還包括標準庫中的許多其他字串處理函式的說明。

6、指標陣列與指向指標的指標

由於指標本身也是變數,所以它們也可以像其他變數一樣儲存在陣列中。

char *lineptr[maxlines]

它表示lineptr是乙個具有maxlines個元素的一維陣列,其中陣列的每個元素是乙個指向字元型物件的指標。即,lineptr[i]是乙個字元指標,而* lineptr[i]是該指標所指向的第i個文字行的首字元。lineptr本身是乙個陣列名字。

7、多維陣列

在c語言中,二維陣列實際上是一種特殊的一維陣列:其元素也是一維陣列。

因此陣列下標應寫成如下形式:

daytab[i][j]

如果要將二維陣列作為變元傳遞給函式,那麼函式的引數說明中應該指明相應陣列的列數。陣列的行數不必指定,因為正如前所述,函式呼叫時傳遞給它的是乙個指向由行向量構成的一維陣列的指標,其中每個行向量是具有n個整數元素的一維陣列。

一般而言,除第一維可以不指定大小外,其餘各維都必須明確指定大小。

8、指標陣列的初始化

month_name函式中包含乙個私有的字串陣列,且當它被呼叫時返回乙個指向正確的字串位置的指標。

指標陣列的初始化語法和早先見過的初始化相似:

char * month_name(int n)

;return ( n < 1 | | n > 12 ) ? name[0] : name[n];

}9、指標與多維陣列

int a[10][20];

int *b[10];

那麼a [3][4]與b[3][4]在語法上都是對乙個整數的合法引用。但a是乙個真正的二維陣列:它分配了200個整數大小的儲存空間,並且用常規的矩陣下標計算公式20×row+col來計算元素a[row][col]的位置。但對b而言,該定義僅僅分配了10個指標而且沒有對它們進行初始化,它們的初始化必須以靜態的方式或用**顯式地進行。

指標陣列的重要優點在

於陣列的每一行可以有不同的長度,即並不是b的每個元素都指向乙個具有20個元素的向量,有些元素可以指向具有兩個元素的向量,有些可以指向具有50個元素的向量,而有些根本就不指向任何向量。

10、命令列變元

在支援c語言的環境中,可以在程式開始執行時將命令列變元或引數傳遞給程式。呼叫主函式時,它可以帶有兩個變元。第乙個變元(習慣上稱做argc,用於變元計數)的值為程式執行時命令列中變元的數目,第二個變元(稱為argv,用於變元向量)是乙個指向字串陣列的指標,其中每個字串對應乙個變元。我們通常用多級指標處理這些字串。

11、指向函式的指標

在c語言中,函式本身不是變數,但可以定義指向函式的指標,這種指標可以被賦值、存放於陣列之中、傳遞給函式及作為函式返回值等等

黑馬程式設計師 C語言 指標

asp.net android ios開發 net培訓 期待與您交流!指標 指標是c語言中非常重要的資料型別 指標變數的定義 int p int是指標指向資料的型別 p是指標變數名稱 只是用來表示變數為指標變數 指標的使用 int a 10 int p p a 或者p a 表示將變數a的記憶體位址賦...

黑馬程式設計師 c語言指標

ios培訓 android培訓 期待與您交流!指標的定義 定義指標和定義乙個變數類似 資料型別 指標變數名 如 int p 表示定義乙個指向整形變數的指標 使用如下 int a 8 int p p a 指標變數 p中存放a的位址,可以通過p中存放的位址,可以訪問變數a中的值。訪問指標變數中存放的位址...

黑馬程式設計師 C語言 指標

一.指標的基本概念 number 10 是什麼意思呢?1.通過number這個位址,找到他指向的空間 2.到這個空間裡,取出裡面儲存的值 普通變數基本格式 變數型別 變數名 指標變數基本格式 變數型別 指標變數名 指標裡面存的是別的變數的位址 p來列印值是0x開頭的,16進製制數字 指標變數在記憶體...