指針用法簡(jiǎn)單介紹
指針,是內(nèi)存單元的編號(hào)。
內(nèi)存條分好多好多小單元,一個(gè)小單元有 8 位,可以存放 8 個(gè) 0 或 1;也就是說,內(nèi)存的編號(hào)不是以位算的,而是以字節(jié)算的,不是一個(gè) 0 或 1 是一個(gè)編號(hào),而是 8 個(gè) 0 或 1 合在一起是一個(gè)編號(hào)。這個(gè)編號(hào),就是地址。
內(nèi)存條就分為好多小格子,一個(gè)格子一個(gè)編號(hào)(地址),相當(dāng)于房子,一個(gè)房子一個(gè)地址。
[所謂的指針,就是地址。]
*p表示的是以p的內(nèi)容為地址的變量
#include?<stdio.h> int?main() { int* p;//p是變量的名字,int*表示變量p存放的是int類型變量的地址 //int* 是p的數(shù)據(jù)類型,p是變量的名字。所謂的int*類型,就是可以存放int類型變量的地址的變量的類型 int?i = 3; /* ??i是整型int類型的變量,可以把變量i的地址放到變量p里 ??&i表示i的地址,&是取址符,表示獲取一個(gè)變量的地址 ?*/ p = &i;//把int類型的變量放到int*類型中 /* ??類似的,double* p只能存放double類型的變量的地址, ??而不能存放int類型的變量的地址 ?*/ ?/* ???關(guān)于對(duì)p=&i的理解: ???p存放了i的地址,所以根據(jù)p可以知道i的位置,進(jìn)而找到i。 ???所以說,p指向i。 ???p不是i,i也不是p;修改i的值不會(huì)改變p的值,修改p的值也不會(huì)影響i的值 ???舉個(gè)例子:[小明](指針變量p)手里拿了一張寫了[小紅家庭地址](變量)的[紙條](指針變量p存儲(chǔ)的i地址&i), ???小紅的家庭發(fā)生任意改變,比如小紅家新買了一輛汽車、丟了一袋垃圾,小明手中的紙條都不會(huì)發(fā)生改變 ???(變量i的值發(fā)生任意改變,+1或者-1,都不會(huì)影響指針變量p里存放的值) ???小明在手里原本寫著小紅家庭地址的紙條上進(jìn)行任意修改,小紅的家的位置也不會(huì)發(fā)生任何變化 ???(原本存放變量i的地址的指針變量p的值發(fā)生任意變化也不會(huì)影響變量i的值) ??*/ ??/* int* p;int i; p和i都是變量,p是能存放其他類型的變量的地址的指針變量,i是只能存放其相應(yīng)類型的值的普通的整型變量。 指針和地址是一個(gè)概念,指針變量也可以叫做地址變量 指針變量p存放了變量i的地址---指針變量p指向了變量i ???*/ printf("%d", *p == i);//1-->說明*p和i的值是一樣的 /* ??如果一個(gè)指針指向了某個(gè)變量,則: ??*指針變量<---等價(jià)于--->普通變量 ??如: ??如果p是指針變量,p存放了普通變量i的地址,則p指向i ??*p<---等價(jià)于--->i ??*p和i可以彼此之間相互替換使用 ?*/ ?/* ??*p表示的是以p的內(nèi)容為地址的變量 ??*/ return?0; } |
指針和指針變量的區(qū)別:
指針就是地址,地址就是指針。
地址[指針]就是內(nèi)存單元的編號(hào)。
指針變量是存放地址[指針]的變量
指針[地址]和指針變量是兩個(gè)不同的概念
但是,有時(shí)候在敘述的時(shí)候,會(huì)把指針變量簡(jiǎn)稱為指針,但是二者不是一回事兒
指針的重要性
·指針可以表示一些復(fù)雜的數(shù)據(jù)結(jié)構(gòu)(比如用鏈表表示的一些數(shù)據(jù)結(jié)構(gòu))
·快速的傳遞數(shù)據(jù)
·使函數(shù)返回一個(gè)以上的值
·能直接訪問硬件
·能夠方便的處理字符串
·是面向?qū)ο笳Z言中引用的基礎(chǔ)
指針是C語言的靈魂
指針的定義
指針就是地址,地址就是指針。那么,指針和地址到底是什么?
地址
·內(nèi)存單元的編號(hào)(就像房門牌號(hào)一樣)
·地址是從0開始的非負(fù)整數(shù)
·[地址的范圍,取決于系統(tǒng)的位數(shù)。在32位系統(tǒng)中,一個(gè)地址的范圍是從0到2^32-1,即從0到4294967295。而在64位系統(tǒng)中,一個(gè)地址的范圍是從0到2^64-1,即從0到18446744073709551615。這些范圍都是基于系統(tǒng)的內(nèi)存大小和尋址能力來確定的。]
指針
·指針就是地址,地址就是指針
·指針變量就是存放內(nèi)存單元編號(hào)的變量,或者說,指針變量就是存放地址/指針的變量
·指針[地址]和指針變量是兩個(gè)不同的概念。但是,有時(shí)候在敘述的時(shí)候,會(huì)把指針變量簡(jiǎn)稱為指針,但是二者不是一回事兒
·指針的本質(zhì)就是一個(gè)操作受限的非負(fù)整數(shù)
[“非負(fù)整數(shù)”,指地址是“從0開始的非負(fù)整數(shù)”。
“操作受限”,指針之間的運(yùn)算只可以進(jìn)行減法,不能進(jìn)行加乘除運(yùn)算]
指針可以進(jìn)行那些運(yùn)算
為什么指針只可以進(jìn)行減法,不能進(jìn)行加乘除運(yùn)算?
兩個(gè)指針相減的結(jié)果是一個(gè)整數(shù)值,表示兩個(gè)指針之間相隔的元素個(gè)數(shù)或者內(nèi)存單元的數(shù)目。 在數(shù)組中,如果兩個(gè)指針指向同一個(gè)數(shù)組的元素,那么它們相減的結(jié)果就是它們之間相隔的元素個(gè)數(shù)。這個(gè)結(jié)果是一個(gè)整數(shù),表示兩個(gè)指針之間有多少個(gè)元素。例如,如果一個(gè)指針指向數(shù)組的第i個(gè)元素,另一個(gè)指針指向數(shù)組的第j個(gè)元素,那么它們的差值就是j-i,表示它們之間相隔的元素個(gè)數(shù)。 同樣地,在內(nèi)存中,如果兩個(gè)指針指向不同的內(nèi)存單元,那么它們相減的結(jié)果就是它們之間相隔的內(nèi)存單元數(shù)目。這個(gè)結(jié)果是一個(gè)整數(shù),表示兩個(gè)指針之間有多少個(gè)內(nèi)存單元。例如,如果一個(gè)指針指向內(nèi)存地址A,另一個(gè)指針指向內(nèi)存地址B,那么它們的差值就是B-A,表示它們之間相隔的內(nèi)存單元數(shù)目。 需要注意的是,兩個(gè)指針相減的結(jié)果是一個(gè)整數(shù)值,而不是地址量。這個(gè)整數(shù)值表示兩個(gè)指針之間相隔的數(shù)據(jù)個(gè)數(shù),而不是它們的內(nèi)存地址差值。因此,在計(jì)算兩個(gè)指針相減的結(jié)果時(shí),應(yīng)該將它們的地址值進(jìn)行整數(shù)相減,而不是將它們的內(nèi)存地址直接相減。 總之,兩個(gè)指針相減的結(jié)果是一個(gè)整數(shù)值,表示兩個(gè)指針之間相隔的元素個(gè)數(shù)或者內(nèi)存單元的數(shù)目。這個(gè)結(jié)果是根據(jù)指針?biāo)赶虻臄?shù)據(jù)類型和內(nèi)存布局來確定的。通過計(jì)算指針之間的差值,程序員可以方便地進(jìn)行數(shù)組遍歷、內(nèi)存管理和其他相關(guān)操作。 |
然而,兩個(gè)指針[地址]相加,就像一個(gè)門牌號(hào)加上另一個(gè)門牌號(hào)一樣,沒有實(shí)際意義。一個(gè)門牌號(hào)在減去另一個(gè)門牌號(hào)得到的整數(shù)就可以表示兩個(gè)房間之間相差了多少個(gè)房間。(比如,房間1006和房間1001之間差了5個(gè)房間;1006-1001=5)。同樣的兩個(gè)指針[地址](門牌號(hào))相乘或相除也沒有實(shí)際意義。
但是指針還可以與整數(shù)進(jìn)行相加減。
指針與整數(shù)的加減表示指針在內(nèi)存空間中向下或向上移動(dòng)整數(shù)個(gè)單位。這個(gè)單位的大小取決于指針?biāo)缸兞康念愋汀@?,如果是指向short型變量的指針,那么每次移動(dòng)2個(gè)字節(jié);如果是指向double型變量的指針,那么每次移動(dòng)8個(gè)字節(jié)。當(dāng)指針變量增加1時(shí),其增加的值等于指向的類型占用的內(nèi)存字節(jié)數(shù)。 指針與整數(shù)的加減運(yùn)算在數(shù)組中位置的移動(dòng)和內(nèi)存地址的偏移中有實(shí)際應(yīng)用。例如,通過將指針變量增加1,可以使其指向下一個(gè)數(shù)組元素,從而實(shí)現(xiàn)數(shù)組的遍歷。同樣地,通過指針與整數(shù)的加減運(yùn)算,可以方便地訪問和操作內(nèi)存中的不同位置,實(shí)現(xiàn)動(dòng)態(tài)內(nèi)存分配、函數(shù)參數(shù)傳遞和數(shù)據(jù)結(jié)構(gòu)實(shí)現(xiàn)等功能。 需要注意的是,指針與整數(shù)的加減運(yùn)算是有單位的,以它所指向數(shù)據(jù)類型的字節(jié)數(shù)為單位進(jìn)行加減。在C語言中,指針加法是以所指向數(shù)據(jù)類型的大小為單位的,例如int類型的指針加1就意味著偏移4個(gè)字節(jié)(假設(shè)int類型占用4個(gè)字節(jié))。 總之,指針與整數(shù)的加減運(yùn)算表示指針在內(nèi)存空間中的移動(dòng)。這種運(yùn)算在數(shù)組索引、指針移動(dòng)和內(nèi)存訪問等操作中具有重要意義,使程序員能夠靈活地操作內(nèi)存和數(shù)據(jù)結(jié)構(gòu),實(shí)現(xiàn)高效的數(shù)據(jù)處理和內(nèi)存管理。 |
就行門牌號(hào)1003,加上一個(gè)整數(shù)2,就變成了門牌號(hào)1005的房間的地址;減去一個(gè)整數(shù)3,就變成了門牌號(hào)1000的房間的地址。
同樣的,指針和整數(shù)之間不能進(jìn)行乘除運(yùn)算,沒有實(shí)際意義。
【如果兩個(gè)指針變量指向的是同一塊連續(xù)空間中的不同存儲(chǔ)單元,這兩個(gè)指針變量才可以相減】
基本類型指針
[知識(shí)點(diǎn)前面已經(jīng)說了,這里看幾個(gè)代碼示例:]
示例一
注意下面的代碼的錯(cuò)誤:
#include?<stdio.h> |
*p指針變量只是進(jìn)行了聲明(給變量起名字和確定類型),而沒有進(jìn)行定義(給變量分配空間),沒有給變量分配空間就無法進(jìn)行初始化(賦值)。如果沒有進(jìn)行定義,那么這個(gè)變量的空間就是不確定的、隨機(jī)的。
如果沒有給指針變量分配內(nèi)存空間,那么這個(gè)指針變量所指向的內(nèi)存位置是不確定的、隨機(jī)的。這意味著,當(dāng)你試圖通過這個(gè)指針進(jìn)行讀寫操作時(shí),你可能會(huì)不小心覆蓋了其他重要的數(shù)據(jù),或者訪問了不屬于你的內(nèi)存空間(稱為“越界”)。這會(huì)導(dǎo)致程序出現(xiàn)未定義的行為,可能是程序崩潰、數(shù)據(jù)損壞或其他不可預(yù)測(cè)的結(jié)果。
示例二
#include?<stdio.h> int?main() { int?i = 5; int* p; int* q; p = &i; //*q=p; /* ??錯(cuò)誤:*q是int類型的變量,p是int*類型的變量,類型不一樣,不能進(jìn)行賦值 ?*/ ?//*q=*p; ?/* ???錯(cuò)誤:*q沒有進(jìn)行定義就給他賦值 ??*/ ??//p=q; ??/* 錯(cuò)誤:q沒定義,q變量存儲(chǔ)的是int*類型的數(shù)據(jù),但是是不確定的、隨機(jī)的、垃圾值 把q存儲(chǔ)的垃圾值賦值給p,p存儲(chǔ)的東西也變成了垃圾值 ???*/ return?0; } |
用指針交換兩個(gè)變量的值
#include?<stdio.h> |
在這個(gè)代碼中,經(jīng)過jiaohuan(int?a,int?b)函數(shù)后,a、b的值沒有發(fā)生變化。因?yàn)殡m然函數(shù)jiaohuan(int?a,int?b)中的參數(shù)變量的名字是a、b,但是這是形參變量,形參變量不會(huì)影響函數(shù)外的變量。即使jiaohuan(int?a,int?b)中的參數(shù)變量的變量名換成別的c、d等等都是一樣的
上述代碼沒有實(shí)現(xiàn)想要的功能,接下來用代碼實(shí)現(xiàn):
#include?<stdio.h> |
對(duì)于函數(shù)jiaohuan(),傳參數(shù)的時(shí)候傳的是&a,&b,不能是a和b。因?yàn)楹瘮?shù)的形參列表里面的參數(shù)是int*類型的。所以這個(gè)函數(shù)傳遞的參數(shù)也只能是指針(地址),而不能是一個(gè)值。
之前不太明白。我想:如果傳參數(shù)的時(shí)候傳的是a,b,為什么函數(shù)的形參列表里面的參數(shù)變量的類型不能是*p、*q類型的?[原理,*p是表達(dá)式而不是變量。對(duì)于int* p,只能是int*類型的p變量而不是int類型的*p變量]
但是,上面這個(gè)代碼也不能實(shí)現(xiàn)交換兩個(gè)變量的值的功能。
因?yàn)椋汉瘮?shù)jiaohuan()交換的不是a、b的值而是p、q的值。p、q是形參,不會(huì)改變實(shí)際的實(shí)參a、b的值。
開始的時(shí)候把a(bǔ)的地址傳遞給了p,把b的地址傳遞給了q。函數(shù)結(jié)束后,p存儲(chǔ)的是b的地址,q存儲(chǔ)的是a的地址。函數(shù)使得p和q存儲(chǔ)的地址進(jìn)行了交換,不會(huì)影響a和b。
沒有任何一個(gè)語言可以改變靜態(tài)變量的位置。變量就相當(dāng)于一個(gè)房子,可以改變房子里的東西,但是無法把房子連根拔起換到別的地方。
形參的變化不會(huì)影響到實(shí)參
#include?<stdio.h> |
這個(gè)代碼就可以實(shí)現(xiàn)交換兩個(gè)變量的值的功能了。
在函數(shù)中,p存儲(chǔ)的是a的地址,*p表示的是int類型的以p的內(nèi)容(a的地址)為地址的“變量”。所以,p指向a,同理,q指向b。
*p等價(jià)于a,*q等價(jià)于b
所以,在變量中,變量(盒子)里的東西(值)進(jìn)行了交換,而不是(盒子)的地址進(jìn)行了交換。
*的三種含義
- 乘法
- 定義指針
- int * p;定義了一個(gè)名字叫p的變量,int*表示p只能存放int類型的變量的地址
- 指針運(yùn)算符
- 該運(yùn)算符放在已經(jīng)定義好的指針變量的前面
- 如果p是一個(gè)已經(jīng)定義好的指針變量,則*p表示以p的內(nèi)容為地址的變量
int* p; *p = a; |
這兩行代碼中,兩個(gè)*的含義是不一樣的?。?!
如何通過被調(diào)函數(shù)修改主函數(shù)中普通變量的值
#include?<stdio.h> |
- 實(shí)參必須為該普通變量的地址
- 形參必須是指針變量
- 在被調(diào)函數(shù)中通過[*形參名=…]的方式可以修改主函數(shù)相關(guān)變量的值
指針和數(shù)組
一維數(shù)組名
一維數(shù)組名是個(gè)指針常量,存放的是一維數(shù)組的第一個(gè)元素的地址
第六行錯(cuò)誤,因?yàn)橐痪S數(shù)組名是常量,不能把一個(gè)值賦值給一個(gè)常量
#include?<stdio.h> |
地址在內(nèi)存中以十六進(jìn)制形式存儲(chǔ)
一維數(shù)組名是個(gè)指針常量,存放的是一維數(shù)組的第一個(gè)元素的地址
那么,以上代碼輸出的十六進(jìn)制應(yīng)該是一樣的
如果一個(gè)函數(shù)要處理一個(gè)一維數(shù)組,則需要接收該數(shù)組的哪些信息?
(確定一個(gè)一維數(shù)組需要幾個(gè)參數(shù)?)
兩個(gè)參數(shù):數(shù)組名、數(shù)組長(zhǎng)度
#include?<stdio.h> |
看下面的例子:
#include?<stdio.h> |
a存放的是一維數(shù)組第一個(gè)元素的地址
*a等價(jià)于a[0]
*(a+1)等價(jià)于a[1]
*(a+2)等價(jià)于a[2]
……
上面的代碼中,函數(shù)f()改變了主函數(shù)中數(shù)組的值:將a傳進(jìn)了函數(shù),*pArr和*a是一樣的,相當(dāng)于兩個(gè)變量都指向了相同的位置。
一個(gè)指針變量占幾個(gè)字節(jié)
假設(shè)p指向char類型變量(1個(gè)字節(jié))
假設(shè)q指向int類型變量(4個(gè)字節(jié))
假設(shè)r指向double類型變量(8個(gè)字節(jié))
p、q、r本身所占字節(jié)數(shù)是否一樣?
#include?<stdio.h> |
這段代碼中,指針的大小是固定的,不管它是指向哪種類型的變量。在大多數(shù)現(xiàn)代的64位系統(tǒng)上,一個(gè)指針的大小是8字節(jié)(64位)。所以,不論是指向字符、整數(shù)還是雙精度浮點(diǎn)數(shù)的指針,它們的大小都是8字節(jié)。32位系統(tǒng)是4字節(jié)
傳統(tǒng)數(shù)組(靜態(tài)內(nèi)存分配)的缺點(diǎn)
- 數(shù)組長(zhǎng)度必須事先指定,且只能是常整數(shù),不能是變量
- 傳統(tǒng)形式定義的數(shù)組,該數(shù)組的內(nèi)存程序員無法手動(dòng)釋放
數(shù)組一旦定義,系統(tǒng)為該數(shù)組分配的空間就會(huì)一直存在,除非該數(shù)組所在的函數(shù)終止。
在一個(gè)函數(shù)運(yùn)行期間,系統(tǒng)為該函數(shù)中數(shù)組所分配的空間會(huì)一直存在,直到該函數(shù)運(yùn)行完畢,數(shù)組的空間才會(huì)被系統(tǒng)釋放。
- 數(shù)組的長(zhǎng)度不能在函數(shù)運(yùn)行的過程中動(dòng)態(tài)的擴(kuò)充或縮?。〝?shù)組的長(zhǎng)度一旦定義就不能再改變了)
- A函數(shù)定義的數(shù)組,在A函數(shù)運(yùn)行期間可以被其他函數(shù)使用,但A函數(shù)運(yùn)行完畢之后,A函數(shù)中的數(shù)組將無法被其他函數(shù)使用
傳統(tǒng)方式定義的數(shù)組不能跨函數(shù)使用
使用動(dòng)態(tài)內(nèi)存分配的動(dòng)態(tài)數(shù)組很好的解決了傳統(tǒng)數(shù)組(靜態(tài)數(shù)組)的這四個(gè)缺陷
malloc函數(shù)
#include?<stdio.h> #include?<malloc.h>//使用malloc函數(shù)需要這個(gè)頭文件 int?main() { int?i = 5;//分配了4個(gè)字節(jié) 靜態(tài)分配 int* p = (int*)malloc(4); /* * 對(duì)于這句代碼,有以下理解: 1、malloc函數(shù)只有一個(gè)形參,這個(gè)形參是整型 2、malloc(4)是請(qǐng)求系統(tǒng)分配4個(gè)字節(jié)的內(nèi)存, 這個(gè)函數(shù)會(huì)返回系統(tǒng)所分配的內(nèi)存的起始地址。 malloc(4)會(huì)返回系統(tǒng)分配的這4個(gè)字節(jié)的第一個(gè)字節(jié)的地址 3、(int*)malloc(4) 強(qiáng)制類型轉(zhuǎn)換,將 malloc 返回的 void* 類型轉(zhuǎn)換為 int* 類型。 malloc函數(shù)會(huì)返回一個(gè) void* 類型的指針[地址],這個(gè)指針指向分配的內(nèi)存的起始地址。 由于 void* 是一個(gè)泛型指針類型,它不包含任何關(guān)于所指向數(shù)據(jù)類型的信息,因此在使用前需要進(jìn)行類型轉(zhuǎn)換。 在 (int*)malloc(4) 中,將 malloc 返回的 void* 指針轉(zhuǎn)換為 int* 類型。 這意味著我們告訴編譯器,我們希望這塊內(nèi)存能夠存儲(chǔ)整數(shù)類型的變量。 4、int* p 定義了一個(gè)名為 p 的指針變量,所以p用于存放int類型的數(shù)據(jù)的地址[指針] 5、最后p指向了4個(gè)字節(jié),但本質(zhì)上p里面只保存了這4個(gè)字節(jié)中的第一個(gè)字節(jié)的地址。 這4個(gè)字節(jié)在用的時(shí)候是作為一個(gè)整體來用的 6、int* p = (int*)malloc(4); 一共分配了12個(gè)字節(jié):其中系統(tǒng)為指針變量p分配了8個(gè)字節(jié)(64位系統(tǒng)) 還分配了4個(gè)字節(jié)的空間,這4個(gè)字節(jié)被p指向(本質(zhì)上p指向的是這4個(gè)字節(jié)的第一個(gè)字節(jié)的地址) 其中,p本身的8個(gè)字節(jié)是靜態(tài)分配的,p指向的4個(gè)字節(jié)是動(dòng)態(tài)分配的 7、p本身的8個(gè)字節(jié)p具有擁有權(quán),而他指向的4個(gè)字節(jié)只具有使用權(quán) 8、*p不是變量,是表達(dá)式。但是*p可以作為變量來使用。*p所指向的內(nèi)存是通過動(dòng)態(tài)分配的 如果int a=*p; 則可以使用變量a代替表達(dá)式*p來使用 */ free(p); //表示把p所指向的內(nèi)存給釋放掉而不會(huì)把p本身所占用的內(nèi)存釋放,所謂釋放內(nèi)存,就是系統(tǒng)收回這段內(nèi)存的使用權(quán),而不會(huì)清空這塊內(nèi)存中的數(shù)據(jù)。被釋放后,整個(gè)程序都失去了對(duì)這段內(nèi)存的使用權(quán)而不僅僅是某個(gè)變量 return?0; } |
?
#include?<stdio.h> #include?<malloc.h>//使用malloc函數(shù)需要這個(gè)頭文件 void?f(int* q) { *q?= 200; //free(q); } int?main() { int* p = (int*)malloc(sizeof(int)); *p = 10; printf("%d\n", *p);//10 f(p); printf("%d\n", *p);//200 return?0; } |
這段代碼:
第一次輸出*p的值,10
第二次輸出*p的值,200
經(jīng)過f()函數(shù),將p中存儲(chǔ)的地址復(fù)制給了q,所以在函數(shù)f()中,*q和*p是一樣的
如果執(zhí)行了free(q),將起不到修改*p的值的作用,還把p指向的空間給釋放掉了,最后輸出的時(shí)候不會(huì)輸出200,而是一個(gè)不確定的隨機(jī)的垃圾值
動(dòng)態(tài)一維數(shù)組的構(gòu)造
#include?<stdio.h> #include?<malloc.h>//使用malloc函數(shù)需要這個(gè)頭文件 int?main() { int?a[5];//int占4個(gè)字節(jié),則本數(shù)組總共包含20個(gè)字節(jié),每4個(gè)字節(jié)被當(dāng)做一個(gè)int變量來使用 //把系統(tǒng)所分配的20個(gè)字節(jié)的前4個(gè)字節(jié)當(dāng)做a[0]來使用,第5~8個(gè)字節(jié)當(dāng)做a[1]來使用…… //只有所在的函數(shù)終止的時(shí)候這20個(gè)字節(jié)才會(huì)被釋放 int?len; printf("請(qǐng)輸入要?jiǎng)?chuàng)建的數(shù)組長(zhǎng)度:\n"); scanf("%d", &len); int* p = (int*)malloc(sizeof(int) * len); //在使用上,和靜態(tài)數(shù)組的使用是一樣的,相當(dāng)于int p[len],只是靜態(tài)定義的數(shù)組不能用len這個(gè)變量 /* 這句代碼分配了20個(gè)字節(jié)的內(nèi)存,p指向了因?yàn)槭菑?qiáng)轉(zhuǎn)成了int*類型, 所以p表示前4個(gè)字節(jié),p+1表示第5~8個(gè)字節(jié),p+2表示第9~12個(gè)字節(jié)…… *p等價(jià)于p[0],*(p+1)等價(jià)于p[1],*(p+2)等價(jià)于p[2]…… 類似的,對(duì)于靜態(tài)定義的數(shù)組,也可以有這樣的寫法 */ return?0; } |
動(dòng)態(tài)內(nèi)存和靜態(tài)內(nèi)存的比較
靜態(tài)內(nèi)存和動(dòng)態(tài)內(nèi)存的區(qū)別主要表現(xiàn)在以下幾個(gè)方面:
1. 分配時(shí)間:靜態(tài)內(nèi)存在程序編譯開始階段分配,動(dòng)態(tài)內(nèi)存在程序運(yùn)行時(shí)分配。
2. 分配位置:靜態(tài)內(nèi)存分配在棧區(qū)或全局/靜態(tài)存儲(chǔ)區(qū),動(dòng)態(tài)內(nèi)存分配在堆區(qū)。
3. 分配方式:靜態(tài)內(nèi)存由編譯器自動(dòng)分配,動(dòng)態(tài)內(nèi)存由程序員手動(dòng)分配。
4. 分配大?。红o態(tài)內(nèi)存大小明確,分配時(shí)就確定;動(dòng)態(tài)內(nèi)存無法確定大小,需要指針來指示位置。
5. 管理方式:靜態(tài)內(nèi)存由編譯器在程序開始運(yùn)行時(shí)分配,并在程序結(jié)束時(shí)釋放;動(dòng)態(tài)內(nèi)存由程序員在運(yùn)行時(shí)分配和釋放。
6. 運(yùn)行速度:靜態(tài)內(nèi)存分配速度快,但占用空間大;動(dòng)態(tài)內(nèi)存分配速度慢,但節(jié)省空間。
7. 安全性:靜態(tài)內(nèi)存由編譯器管理,安全性較高;動(dòng)態(tài)內(nèi)存管理需要程序員手動(dòng)管理,容易出錯(cuò),安全性較低。
綜上所述,靜態(tài)內(nèi)存和動(dòng)態(tài)內(nèi)存的區(qū)別主要表現(xiàn)在分配時(shí)間、分配位置、分配方式、分配大小、管理方式、運(yùn)行速度和安全性等方面。在實(shí)際編程中,根據(jù)需要選擇使用哪種類型的內(nèi)存,以提高程序的效率和安全性。
多級(jí)指針
文章來源:http://www.zghlxwxcb.cn/news/detail-811063.html
無論是幾級(jí)指針變量,都是之占8個(gè)字節(jié)文章來源地址http://www.zghlxwxcb.cn/news/detail-811063.html
到了這里,關(guān)于C語言/c++指針詳細(xì)講解【超詳細(xì)】【由淺入深】的文章就介紹完了。如果您還想了解更多內(nèi)容,請(qǐng)?jiān)谟疑辖撬阉鱐OY模板網(wǎng)以前的文章或繼續(xù)瀏覽下面的相關(guān)文章,希望大家以后多多支持TOY模板網(wǎng)!