大家好,c語(yǔ)言指針的作用相信很多的網(wǎng)友都不是很明白,包括c語(yǔ)言指針怎么理解也是一樣,不過(guò)沒(méi)有關(guān)系,接下來(lái)就來(lái)為大家分享關(guān)于c語(yǔ)言指針的作用和c語(yǔ)言指針怎么理解的一些知識(shí)點(diǎn),大家可以關(guān)注收藏,免得下次來(lái)找不到哦,下面我們開(kāi)始吧!
C語(yǔ)言指針怎樣快速掌握指針用處大嗎
C語(yǔ)言指針就是這門語(yǔ)言的靈魂,說(shuō)難學(xué),那肯定是有難度的,畢竟這是業(yè)界公認(rèn)的。但是如果你熟練掌握了指針的話,它又將會(huì)成為你手中的一柄利器。下面就詳細(xì)的分享一下指針該如何深入的去理解它以及如何熟練的應(yīng)用它
理解指針首先,你需要掌握兩個(gè)運(yùn)算符“*”和“&”;
“&”運(yùn)算符:取對(duì)象在內(nèi)存中的地址
“*”運(yùn)算符:取內(nèi)存中地址上的對(duì)象(值);
大家一定要深刻的理解上面兩個(gè)運(yùn)算符,然后才能去進(jìn)一步理解指針;
inta=100;這一行代碼我想大家都沒(méi)問(wèn)題。那么“&a”返回的就是對(duì)象(變量)a在內(nèi)存中的地址,它是一個(gè)16進(jìn)制數(shù)。
然后用“*”號(hào)去a的地址去取對(duì)象:“*(&a)”,,就能取到對(duì)象a,也就就是100;
接下來(lái)進(jìn)入重點(diǎn)了,指針,本身也是一個(gè)變量(對(duì)象),它本身占用內(nèi)存,但是它只存地址(別人的地址),它存的誰(shuí)的地址我們就稱它為指向誰(shuí)的指針;
int*p=&a;int*p_2=newint(200);先不管他的類型申明,只看變量本身p和p_2。前面講到指針存放的是對(duì)象的地址,那么可以理解為指針是一個(gè)地址變量,那么賦值的話就需要也賦一個(gè)地址給它一個(gè)地址。int*和char*都可以表示地址類型,它們的區(qū)別就是地址所存的值得類型不同,一個(gè)是存整型,一個(gè)是存字符型;
對(duì)指針取值的話,就是用“*”號(hào),后面接對(duì)象地址,也就是指針變量,所以*p和*p_2就分別是a和200;
指針的運(yùn)用指針并不是C/C++獨(dú)有的,像C#和java等其實(shí)也是有指針的,只不過(guò)都被語(yǔ)言本身用其他的方式替代和封裝了一般程序員接觸不到,C/C++就不一樣,它是直接將指針暴露給開(kāi)發(fā)者,因?yàn)榇蟛糠譅可娴街羔樀亩寂c內(nèi)存有關(guān),而計(jì)算機(jī)內(nèi)存很重要,萬(wàn)一出什么問(wèn)題可能系統(tǒng)都會(huì)崩潰,下面就簡(jiǎn)單來(lái)看一下程序在運(yùn)行時(shí)指針與內(nèi)存之間到底是個(gè)什么樣的關(guān)系:
先看一段代碼:
#include<stdio.h>
#include<string>
#include<iostream>
#include<time.h>
usingnamespacestd;
classpeople
{
public:
people();
~people();
stringName;
intage;
boolsex;
charinfo[1024];
voidrun(){}
voideat(){}
private:
};
people::people()
{
}
people::~people()
{
}
intmain()
{
people*p1=newpeople();
cout<<p1<<endl;
cout<<&p1<<endl;
cout<<sizeof(p1)<<endl;
cout<<sizeof(*p1)<<endl;
system("pause");
return0;
}
直接運(yùn)行看結(jié)果:
分析接下來(lái)來(lái)一一進(jìn)行分析:
首先people*p1=newpeople();這一句是類的一個(gè)實(shí)例化,系統(tǒng)會(huì)給people實(shí)例化一個(gè)對(duì)象*p并且給它在堆上開(kāi)辟空間,注意是在堆上,開(kāi)辟的空間用來(lái)存儲(chǔ)對(duì)象的數(shù)據(jù)。數(shù)據(jù)包括哪些?就是對(duì)象的屬性和虛函數(shù)指針,但是函數(shù)并不存儲(chǔ)在各對(duì)象中。因此run()和eat()方法是不存在對(duì)象*p指向的內(nèi)存處的。
cout<<p1<<endl;輸出的是00279360,這是一個(gè)地址,是系統(tǒng)給newpeople()對(duì)象分配的地址。
cout<<&p1<<endl;輸出的是0012FD90,這也是地址,但這是指針變量p本身的地址。
cout<<sizeof(p1)<<endl;
cout<<sizeof(*p1)<<endl;
通過(guò)這兩個(gè)輸出就能有更清晰的認(rèn)識(shí)了,p1本身只占用4個(gè)字節(jié)的空間,而它所指向的對(duì)象的地址所占的空間就很大,等于類中所有數(shù)據(jù)類型所占空間之和。
接下來(lái)在main函數(shù)里寫(xiě)一點(diǎn)邏輯:
圖解我們來(lái)看一下程序運(yùn)行時(shí)間,指針和內(nèi)存是怎么工作的。這里畫(huà)一個(gè)圖給大家:
程序在運(yùn)行時(shí),數(shù)據(jù)主要是存儲(chǔ)在棧、堆、代碼區(qū)、全局區(qū)。代碼區(qū)主要就是存代碼中出現(xiàn)的一些字符常量、方法等,比如這里代碼中給對(duì)象的Name屬性賦的值“xiaoli”之類的都是存在此處,然后我們通過(guò)new出來(lái)的對(duì)象,都是由堆通過(guò)計(jì)算好類中各屬性所需空間然后開(kāi)辟出來(lái)的。這里p3不是通過(guò)new開(kāi)辟出來(lái)的,所以他是存在棧上的并且地址是固定的,是不能更改的,而p1和p2是能更改的。
改變地址如此,我們?nèi)齻€(gè)對(duì)象互相賦值后會(huì)發(fā)生什么呢?
對(duì)比代碼和輸出結(jié)果我們發(fā)現(xiàn)了什么?賦值后p1和p2本身的地址并無(wú)改變,但是他所指向的內(nèi)存都編程p3所在的內(nèi)存了。下面用圖解給大家看一下:
注意,此處原來(lái)的p1和p2指向的內(nèi)存由于是new出來(lái)的我們需要手動(dòng)釋放它。所以我們?cè)谥匦沦x值之前要將這兩塊內(nèi)存刪除掉deletep2;deletep1;
改變地址的值如果我將代碼中的p2=&p3;換成*p2=p3呢?我們看下輸出結(jié)果:
造成這種情況的原因,其實(shí)這就牽涉到指針的兩種賦值問(wèn)題:一種是改變指向的地址,一種是改變本身指向地址的值p2=&p3是改變指向地址,*p2=p3是改變指向地址的值。
一直沒(méi)明單片機(jī)C語(yǔ)言的指針這塊內(nèi)容,在什么情況下會(huì)用到指針呢
作為一名長(zhǎng)期使用C語(yǔ)言進(jìn)行開(kāi)發(fā)的老司機(jī),我來(lái)回答一下C語(yǔ)言指針的問(wèn)題。
首先、C語(yǔ)言指針的本質(zhì)是什么?C語(yǔ)言指針的本質(zhì)是內(nèi)存變量,是內(nèi)存單元的編號(hào)。內(nèi)存單元是以字節(jié)為單位的。所以指針就是字節(jié)的編號(hào)。如下圖所示,一個(gè)4G內(nèi)存的編號(hào),指針的值其實(shí)就是內(nèi)存編號(hào)。
其次、搞清楚變量和指針的關(guān)系變量對(duì)應(yīng)的是具體的內(nèi)存,變量的內(nèi)容就是內(nèi)存中保存的數(shù)據(jù)。
比如,我們定義一個(gè)變量uint8_ta=10,假如a的位置是0,也就是上圖中0位置的內(nèi)存中保存的數(shù)據(jù)是10;
我們?cè)賮?lái)看指針,定義指針uint8_t*b=&a,我們知道&的含義是取地址,那么根據(jù)上面的假設(shè)變量a位于地址0,那么&a也就是0,此時(shí)指針變量b的值也就是0.
如果不好理解指針定義uint8_t*b=&a,我們可以變通一下:
(uint8_t*)b=&a,把(uint8_t*)當(dāng)做一個(gè)新的數(shù)據(jù)類型就好理解了,其實(shí)我們實(shí)際的編程中,也通常會(huì)這么定義:typeofuint8_t*uint8_p
uint8_pb=&a;
這樣b就更像是一個(gè)變量了,理解起來(lái)更容易了。
第三、指針單元和內(nèi)存指針每個(gè)單元代表多少個(gè)內(nèi)存呢?這要看指針的類型
比如,char*a,shortint*b,int*c,longint*d等
指針?biāo)傅拿糠輧?nèi)存數(shù)量為1個(gè)字節(jié),2個(gè)字節(jié),4個(gè)字節(jié),8個(gè)字節(jié),也就是每個(gè)變量類型所占的內(nèi)存單元。
假設(shè)a、b、c、d四個(gè)指針變量值均為100,分別做自加運(yùn)算后,指針的值是多少呢?
a++;
b++;
c++;
d++;
你能猜出,a、b、c、d的值分別是多少嗎?
答案是:101,102,104,108.
也就是每次指針移動(dòng)一個(gè)變量類型對(duì)應(yīng)的內(nèi)存數(shù),這個(gè)可以在keil開(kāi)發(fā)環(huán)境上面通過(guò)模擬環(huán)境驗(yàn)證,有興趣的可以自行驗(yàn)證一下。
最后、指針的優(yōu)勢(shì)和應(yīng)用場(chǎng)景優(yōu)勢(shì):1.效率高;2、靈活,可以訪問(wèn)任意位置的內(nèi)存數(shù)據(jù);3、作為函數(shù)參數(shù)傳遞,只需要傳遞4個(gè)字節(jié),比數(shù)組傳值節(jié)省內(nèi)存拷貝時(shí)間。
應(yīng)用場(chǎng)景:1.函數(shù)中交換兩個(gè)變量的值
在學(xué)習(xí)函數(shù)時(shí),交換兩個(gè)數(shù)的值,做一個(gè)swap函數(shù),傳遞值進(jìn)去,也可以將兩個(gè)值交換過(guò)來(lái),沒(méi)問(wèn)題,可是離開(kāi)swap就沒(méi)有用了,為什么?因?yàn)閭鬟M(jìn)去的是兩個(gè)值。如果傳遞的是指針就沒(méi)有問(wèn)題。因?yàn)橹羔槀鬟f過(guò)去的是兩個(gè)變量的地址,變量的位置不變。
2.函數(shù)通過(guò)指針?lè)祷囟鄠€(gè)值
3.函數(shù)返回運(yùn)算的狀態(tài),結(jié)果通過(guò)指針?lè)祷?/p>
…………
指針的弊端指針是C語(yǔ)言的靈魂所在,通常說(shuō)C語(yǔ)言是“低級(jí)”語(yǔ)言的原因,很大程度上也是因?yàn)镃語(yǔ)言指針的問(wèn)題,C語(yǔ)言指針讓開(kāi)發(fā)者可以訪問(wèn)任意內(nèi)存位置的數(shù)據(jù)。這是其他語(yǔ)音沒(méi)有辦法達(dá)到的。也正因?yàn)橹羔槪珻語(yǔ)言也很容易出錯(cuò),最常見(jiàn)的問(wèn)題是地址越界,如果地址越界,讀寫(xiě)了不該讀寫(xiě)的內(nèi)容會(huì)直接導(dǎo)致系統(tǒng)崩潰,而且這種問(wèn)題很難定位,因?yàn)檎Z(yǔ)法上是沒(méi)有錯(cuò)誤的,編譯的時(shí)候無(wú)法檢查出來(lái)。
對(duì)于C語(yǔ)言指針的問(wèn)題,大家有什么意見(jiàn),歡迎留言討論。
C語(yǔ)言的指針有什么用
指針是C語(yǔ)言中一個(gè)重要的概念,可以用來(lái)間接操縱變量和數(shù)據(jù)結(jié)構(gòu)。主要的用途有以下幾個(gè)方面:
內(nèi)存管理:指針可以用來(lái)管理內(nèi)存,包括動(dòng)態(tài)內(nèi)存分配和釋放,以及操縱和存儲(chǔ)數(shù)據(jù)結(jié)構(gòu)等。
傳遞引用:指針可以傳遞變量的引用而不是值,這樣可以有效地減少內(nèi)存使用和運(yùn)行時(shí)間,并且使函數(shù)調(diào)用更加高效。
操作數(shù)據(jù)結(jié)構(gòu):指針可以被用來(lái)操縱各種數(shù)據(jù)結(jié)構(gòu),如鏈表、樹(shù)、堆棧等,可以方便地進(jìn)行數(shù)據(jù)操作。
函數(shù)返回:指針可以用作函數(shù)的返回值,可以返回結(jié)構(gòu)體和動(dòng)態(tài)分配內(nèi)存的數(shù)組等數(shù)據(jù)結(jié)構(gòu)。
字符串處理:指針可以用來(lái)處理字符數(shù)組和字符串,可以有效地訪問(wèn)和操作這些數(shù)據(jù)類型。
因此,指針是C語(yǔ)言中非常重要的一個(gè)概念,它提供了許多強(qiáng)大的功能,可以用來(lái)管理內(nèi)存、優(yōu)化代碼、操作數(shù)據(jù)結(jié)構(gòu)等。無(wú)論是系統(tǒng)程序、底層程序還是應(yīng)用程序,指針在C語(yǔ)言的編程中都有著廣泛的應(yīng)用。
都說(shuō)C語(yǔ)言的指針很難,用不好很容易出錯(cuò),那為何還要用指針呢你能舉例說(shuō)說(shuō)嗎
1.分析問(wèn)題
整個(gè)問(wèn)題,從提問(wèn)者的角度,等價(jià)于兩個(gè)子問(wèn)題:
子問(wèn)題1:為什么C語(yǔ)言要引入指針?
子問(wèn)題2:指針怎么才能用好?
2.子問(wèn)題1的分析現(xiàn)在來(lái)分析子問(wèn)題1。要回到這個(gè)問(wèn)題,要回顧計(jì)算機(jī)程序的執(zhí)行原理:
現(xiàn)代通用計(jì)算機(jī)基本上都遵循馮·諾依曼結(jié)構(gòu)。
馮·諾依曼結(jié)構(gòu)的精髓在于:將計(jì)算機(jī)指令與數(shù)據(jù)一視同仁,都放入內(nèi)存中處理。所以計(jì)算機(jī)程序執(zhí)行的過(guò)程,實(shí)際上就是不斷從內(nèi)存中取出指令,再?gòu)膬?nèi)存中取出數(shù)據(jù),指令作用于數(shù)據(jù)得到結(jié)果,結(jié)果再放回內(nèi)存的過(guò)程。
從這個(gè)過(guò)程可以看出,程序的整個(gè)運(yùn)行都是圍繞內(nèi)存進(jìn)行的。既然指令和數(shù)據(jù)都放在內(nèi)存中,那么執(zhí)行哪條指令、取哪個(gè)數(shù)據(jù)、結(jié)果放到哪里,都需要精確定位內(nèi)存的具體位置。
C語(yǔ)言作為開(kāi)發(fā)Unix操作系統(tǒng)而創(chuàng)造出來(lái)的編程語(yǔ)言,天然需要具備操作系統(tǒng)底層的能力;而從上述程序運(yùn)行的視角來(lái)看,所謂的系統(tǒng)底層能力,核心在于對(duì)內(nèi)存位置的定位能力。C語(yǔ)言用于對(duì)內(nèi)存進(jìn)行定位的“武器”就是指針。
一言以蔽之:C語(yǔ)言之所以引入指針,是由C語(yǔ)言誕生的歷史背景和所要承載的歷史使命決定的——開(kāi)發(fā)操作系統(tǒng),要用強(qiáng)大的操控系統(tǒng)底層的能力,系統(tǒng)底層的核心是對(duì)內(nèi)存的定位操作。
3.子問(wèn)題2的分析很多同學(xué)被指針搞懵的原因在于:大陸的C語(yǔ)言入門的教材基本上都是譚浩強(qiáng)的《C語(yǔ)言程序設(shè)計(jì)》,這本教材講述指針過(guò)于繁瑣,沒(méi)有抓住指針的本質(zhì)。
指針的本質(zhì)就是內(nèi)存地址。
記住這一點(diǎn)之后,你就可以游刃有余了。以下筆者對(duì)初學(xué)者最容易暈菜的幾個(gè)概念進(jìn)行最凝練的解釋。
3.1多級(jí)指針一級(jí)指針就是一次性指向目標(biāo)內(nèi)存地址、二級(jí)指針就是分兩段指向最終目標(biāo)地址(第一級(jí)相當(dāng)于先指向一個(gè)“中間驛站”,第二級(jí)再?gòu)摹爸虚g驛站”指向最終目標(biāo)地址)……依次類推,這樣哪怕給你一個(gè)N級(jí)指針,你也不會(huì)懵逼。
3.2指針數(shù)組與數(shù)組指針說(shuō)白了,考的并不是計(jì)算機(jī)知識(shí),考的是語(yǔ)文知識(shí):)
兩個(gè)術(shù)語(yǔ)都是偏正短語(yǔ):前者的被修飾詞(中心詞)是數(shù)組,后者的被修飾詞(中心詞)是指針;前者這個(gè)數(shù)組里的每個(gè)元素都是指針,后者這個(gè)指針指向的是一個(gè)數(shù)組(一片連續(xù)的內(nèi)存區(qū))。
c語(yǔ)言中使用指針和不使用指針的差別
在C語(yǔ)言中,使用指針和不使用指針之間存在一些重要的差別:
1.內(nèi)存管理:使用指針可以直接訪問(wèn)和操作內(nèi)存地址,從而允許更靈活地管理內(nèi)存。指針可以用于動(dòng)態(tài)分配內(nèi)存、釋放內(nèi)存以及在函數(shù)之間傳遞大型數(shù)據(jù)結(jié)構(gòu)。而不使用指針時(shí),只能使用靜態(tài)分配的內(nèi)存,無(wú)法進(jìn)行動(dòng)態(tài)內(nèi)存管理。
2.數(shù)據(jù)傳遞:使用指針可以通過(guò)引用傳遞方式在函數(shù)之間傳遞數(shù)據(jù),這樣可以避免數(shù)據(jù)的復(fù)制,提高程序的效率。而不使用指針時(shí),需要通過(guò)值傳遞方式將數(shù)據(jù)復(fù)制到函數(shù)中,可能會(huì)浪費(fèi)時(shí)間和內(nèi)存。
3.數(shù)據(jù)結(jié)構(gòu)和算法:使用指針可以更方便地操作和修改數(shù)據(jù)結(jié)構(gòu),例如鏈表、樹(shù)等。指針還可以實(shí)現(xiàn)一些高級(jí)算法,如動(dòng)態(tài)內(nèi)存分配、遞歸等。而不使用指針時(shí),可能需要更多的代碼和額外的數(shù)據(jù)結(jié)構(gòu)來(lái)實(shí)現(xiàn)相同的功能。
4.空間效率:使用指針可以減少內(nèi)存的使用,特別是在處理大型數(shù)據(jù)結(jié)構(gòu)和數(shù)組時(shí)。指針可以節(jié)省內(nèi)存,因?yàn)樗鼈冎恍枰鎯?chǔ)內(nèi)存地址,而不是實(shí)際數(shù)據(jù)本身。而不使用指針時(shí),需要更多的內(nèi)存來(lái)存儲(chǔ)數(shù)據(jù)本身。
總結(jié):使用指針可以提供更靈活的內(nèi)存管理、更高效的數(shù)據(jù)傳遞、更方便的數(shù)據(jù)結(jié)構(gòu)和算法操作,以及更高的空間效率。然而,指針的使用也需要更多的注意和謹(jǐn)慎,因?yàn)殄e(cuò)誤的指針操作可能導(dǎo)致內(nèi)存泄漏、段錯(cuò)誤等問(wèn)題。因此,在使用指針時(shí)需要謹(jǐn)慎處理內(nèi)存和指針的生命周期。
c語(yǔ)言指針有什么用
C語(yǔ)言中,指針的使用非常廣泛,因?yàn)槭褂弥羔樛梢陨筛咝А⒏o湊的代碼。總的來(lái)說(shuō),使用指針有如下好處:
1)指針的使用使得不同區(qū)域的代碼可以輕易的共享內(nèi)存數(shù)據(jù),這樣可以使程序更為快速高效;
2)C語(yǔ)言中一些復(fù)雜的數(shù)據(jù)結(jié)構(gòu)往往需要使用指針來(lái)構(gòu)建,如鏈表、二叉樹(shù)等。
3)C語(yǔ)言是傳值調(diào)用,而有些操作傳值調(diào)用是無(wú)法完成的,如通過(guò)被調(diào)函數(shù)修改調(diào)用函數(shù)的對(duì)象,但是這種操作可以由指針來(lái)完成,而且并不違背傳值調(diào)用。
好了,本文到此結(jié)束,如果可以幫助到大家,還望關(guān)注本站哦!