1.取一個變量的值,可通過直接與間接的方式
直接:訪問變量
間接:通過變量的內存地址來獲取變量的值。
存放內存地址的變量就是指針變量。
2.定義指針變量的語法:類型* 變量名
&:取地址運算符,取變量的內存地址;(單目運算符)
*:取變量運算符,讀取指針所指的變量。
3.對於指針變量,有兩個規則:
(1)定義指針變量時,必須用*來標識定義指針變量;
(2)c語言是強類型語言,指針變量需要先定義再使用,而且一旦指定指針的類型,則該指針變量只能指向指定類型的變量。
4.指針可作為函數形參:
#import<Foundation/Foundation.h>
void swap(int* a,int* b)
{
int tmp=*a;
*a=*b;
*b=tmp
a=b=nil;
}
int main(int argc,char* argv[])
{
@autoreleasepool{
int m=5;
int n=9;
//m,n的值發生對調
//如果函數參數使用普通變量,m,n的值不受函數的影響
swap(m,n);
NSLog(@"%d,%d",m,n);
}
return 0;
}
原因:因為函數傳遞方式是值傳遞,直接使用變量的副本。如果函數變量是普通變量,那麼函數對變量所做的修改都無法改變變量本身。
如果函數需要對變量的值進行修改,則需要傳入該函數的指針,並在函數中對指針所指的變量值進行修改。
以函數swap(a,b)為例:
指針*a 指向m,取m的值(m=5)賦給tmp,而tmp又將值賦給了指針*b,指針*b代表了n的內存地址,從而改變了n的值(地址傳遞);
如果形參是普通變量:因為是值傳遞,使用的是m,n的副本,所以只是單純的把m,n復制一份給a,b;a,b怎麼變都不會來影響m,n。
5.指針與數組
(1)數組的首地址就是數組的地址。
int arr[];
&arr[0]=&arr[];
不能將整數值直接賦值給指針變量。
(2)指針的賦值方式
int* p;int* pt;int a;
p=&a;//將a的內存地址賦給p;
p=&arr[i];//將數組中的某個元素地址賦給p;
p=arr;//將數組的首地址賦給p;
p=pt;//將pt保存的內存地址賦給p;
(3)數組指針的運算
加減一個整數n:指針的地址加減(n*變量大小個字節);
當兩個指針指向同一個數組時,兩指針相減表示 所指的兩個數組元素之間相隔的元素個數;
當兩個指針指向同一個數組時,指向前面元素的指針小於指向後面的。
(4)數組變量是指針常量,因為數組地址是不可變的。
6.數組變量作為函數參數:
傳入的是指向數值的指針,在函數中對數組元素所做的修改將會影響到原來的數組。
快速排序法:
//
7.字符串與指針
c語言中 用字符數組表示 字符串,所以字符串指針就是指向字符數組首地址的數組指針。
字符串(字符數組),字符指針(指向字符數組的指針)
ps:需要把指針定義成字符型指針。
字符數組不能重新賦值,只能在定義時賦值;
8.函數與指針
指針也可以表示函數入口
指針指向函數入口步驟:
(1)定義函數指針變量:
語法:(函數返回值類型*)(函數指針變量名)()
(2)將函數賦值給指針變量:
(3)使用函數指針變量調用函數:
語法:(*函數指針變量名)(參數);
函數指針作為另一個函數參數:
定義一個函數時,但某些處理邏輯沒有確定下來,即部分代碼需要動態改變時,可使用函數指針作為參數。
函數指針作為返回類型:
為了保證返回的指針有效,有兩種方式:
(1)指向函數中的局部變量時,使用static關鍵字;
(2)讓指針指向暫時不會釋放的數據。
9.指針數組
聲明指針數組的格式:數據類型 *數組變量名[長度]
注意:類型(* 數組變量)[長度]:表示指向一位數組的指針.