導航:首頁 > 源碼編譯 > mdk編譯重復代碼

mdk編譯重復代碼

發布時間:2025-05-09 20:50:22

❶ C++中如何表示從2到10

綜合自網路



C語言在嵌入式學習中是必備的知識,審核大部分操作都要圍繞C語言進行,而其中有三塊「難啃的硬骨頭」幾乎是公認級別的。

指針公認最難理解的概念,也是讓很多初學者選擇放棄的直接原因。

指針之所以難理解,因為指針本身就是一個變數,是一個非常特殊的變數,專門存放地址的變數,這個地址需要給申請空間才能裝東西,而且因為是個變數可以中間賦值,這么一倒騰很多人就開始犯暈了,繞不開彎了。C語言之所以被很多高手所喜歡,就是指針的魅力,中間可以靈活的切換,執行效率超高,這點也是讓小白暈菜的地方。

指針是學習繞不過去的知識點,而且學完C語言,下一步緊接著切換到數據結構和演算法,指針是切換的重點,指針搞不定下一步進行起來就很難,會讓很多人放棄繼續學習的勇氣。

指針直接對接內存結構,常見的C語言裡面的指針亂指,數組越界根本原因就是內存問題。在指針這個點有無窮無盡的發揮空間。很多編程的技巧都在此集結。

指針還涉及如何申請釋放內存,如果釋放不及時就會出現內存泄露的情況,指針是高效好用,但不徹底搞明白對於有些人來說簡直就是噩夢。

在概念方面問題可以參見此前推文《對於C語言指針最詳盡的講解》,那麼在指針方面可以參見一下大神的經驗:

復雜類型說明

要了解指針,多多少少會出現一些比較復雜的類型。所以先介紹一下如何完全理解一個復雜類型。

要理解復雜類型其實很簡單,一個類型里會出現很多運算符,他們也像普通的表達式一樣,有優先順序,其優先順序和運算優先順序一樣。

所以筆者總結了一下其原則:從變數名處起,根據運算符優先順序結合,一步一步分析。

下面讓我們先從簡單的類型開始慢慢分析吧。

int p;

這是一個普通的整型變數

int p;

首先從P處開始,先與結合,所以說明P是一個指針。然後再與int結合,說明指針所指向的內容的類型為int型,所以P是一個返回整型數據的指針

int p[3];

首先從P處開始,先與[]結合,說明P是一個數組。然後與int結合,說明數組里的元素是整型的,所以P是一個由整型數據組成的數組。

int *p[3];

首先從P處開始,先與[]結合,因為其優先順序比高,所以P是一個數組。然後再與結合,說明數組里的元素是指針類型。之後再與int結合,說明指針所指向的內容的類型是整型的,所以P是一個由返回整型數據的指針所組成的數組。

int (*p)[3];

首先從P處開始,先與結合,說明P是一個指針。然後再與[]結合(與"()"這步可以忽略,只是為了改變優先順序),說明指針所指向的內容是一個數組。之後再與int結合,說明數組里的元素是整型的。所以P是一個指向由整型數據組成3個整數的指針。

int **p;

首先從P開始,先與結合,說明P是一個指針。然後再與結合,說明指針所指向的元素是指針。之後再與int結合,說明該指針所指向的元素是整型數據。由於二級指針以及更高級的指針極少用在復雜的類型中,所以後面更復雜的類型我們就不考慮多級指針了,最多隻考慮一級指針。

int p(int);

從P處起,先與()結合,說明P是一個函數。然後進入()里分析,說明該函數有一個整型變數的參數,之後再與外面的int結合,說明函數的返回值是一個整型數據。

int (*p)(int);

從P處開始,先與指針結合,說明P是一個指針。然後與()結合,說明指針指向的是一個函數。之後再與()里的int結合,說明函數有一個int型的參數,再與最外層的int結合,說明函數的返回類型是整型,所以P是一個指向有一個整型參數且返回類型為整型的函數的指針。

int (p(int))[3];

可以先跳過,不看這個類型,過於復雜。從P開始,先與()結合,說明P是一個函數。然後進入()裡面,與int結合,說明函數有一個整型變數參數。然後再與外面的結合,說明函數返回的是一個指針。之後到最外面一層,先與[]結合,說明返回的指針指向的是一個數組。接著再與結合,說明數組里的元素是指針,最後再與int結合,說明指針指向的內容是整型數據。所以P是一個參數為一個整數據且返回一個指向由整型指針變數組成的數組的指針變數的函數。

說到這里也就差不多了。理解了這幾個類型,其它的類型對我們來說也是小菜了。不過一般不會用太復雜的類型,那樣會大大減小程序的可讀性,請慎用。這上面的幾種類型已經足夠我們用了。

細說指針

指針是一個特殊的變數,它裡面存儲的數值被解釋成為內存里的一個地址。

要搞清一個指針需要搞清指針的四方面的內容:指針的類型、指針所指向的類型、指針的值或者叫指針所指向的內存區、指針本身所佔據的內存區。讓我們分別說明。

先聲明幾個指針放著做例子:

(1)int*ptr;

(2)char*ptr;

(3)int**ptr;

(4)int(*ptr)[3];

(5)int*(*ptr)[4];
指針的類型

從語法的角度看,小夥伴們只要把指針聲明語句里的指針名字去掉,剩下的部分就是這個指針的類型。這是指針本身所具有的類型。

讓我們看看上述例子中各個指針的類型:

(1)intptr;//指針的類型是int

(2)charptr;//指針的類型是char

(3)intptr;//指針的類型是int

(4)int(ptr)[3];//指針的類型是int()[3]

(5)int*(ptr)[4];//指針的類型是int(*)[4]

怎麼樣?找出指針的類型的方法是不是很簡單?

指針所指向的類型

當通過指針來訪問指針所指向的內存區時,指針所指向的類型決定了編譯器將把那片內存區里的內容當做什麼來看待。

從語法上看,小夥伴們只需把指針聲明語句中的指針名字和名字左邊的指針聲明符*去掉,剩下的就是指針所指向的類型。

上述例子中各個指針所指向的類型:

(1)intptr; //指針所指向的類型是int

(2)char*ptr; //指針所指向的的類型是char*

(3)int*ptr; //指針所指向的的類型是int*

(4)int(*ptr)[3]; //指針所指向的的類型是int(*)[3]

(5)int*(*ptr)[4]; //指針所指向的的類型是int*(*)[4]

在指針的算術運算中,指針所指向的類型有很大的作用。

指針的類型(即指針本身的類型)和指針所指向的類型是兩個概念。當小夥伴們對C 越來越熟悉時,就會發現,把與指針攪和在一起的"類型"這個概念分成"指針的類型"和"指針所指向的類型"兩個概念,是精通指針的關鍵點之一。

筆者看了不少書,發現有些寫得差的書中,就把指針的這兩個概念攪在一起了,所以看起書來前後矛盾,越看越糊塗。

指針的值

即指針所指向的內存區或地址。

指針的值是指針本身存儲的數值,這個值將被編譯器當作一個地址,而不是一個一般的數值。

在32位程序里,所有類型的指針的值都是一個32位整數,因為32位程序里內存地址全都是32位長。指針所指向的內存區就是從指針的值所代表的那個內存地址開始,長度為si zeof(指針所指向的類型)的一片內存區。

以後,我們說一個指針的值是XX,就相當於說該指針指向了以XX為首地址的一片內存區域;我們說一個指針指向了某塊內存區域,就相當於說該指針的值是這塊內存區域的首地址。

指針所指向的內存區和指針所指向的類型是兩個完全不同的概念。在例一中,指針所指向的類型已經有了,但由於指針還未初始化,所以它所指向的內存區是不存在的,或者說是無意義的。

以後,每遇到一個指針,都應該問問:這個指針的類型是什麼?指針指的類型是什麼?該指針指向了哪裡?

指針本身所佔據的內存區

指針本身佔了多大的內存?只要用函數sizeof(指針的類型)測一下就知道了。在32位平台里,指針本身占據4個位元組的長度。指針本身占據的內存這個概念在判斷一個指針表達式是否是左值時很有用。

0x02 函數

面向過程對象模塊的基本單位,以及對應各種組合,函數指針,指針函數

一個函數就是一個業務邏輯塊,是面向過程,單元模塊的最小單元,而且在函數的執行過程中,形參,實參如何交換數據,如何將數據傳遞出去,如何設計一個合理的函數,不單單是解決一個功能,還要看是不是能夠復用,避免重復造輪子。

函數指針和指針函數,表面是兩個字面意思的互換實際上含義截然不同,指針函數比較好理解,就是返回指針的一個函數,函數指針這個主要用在回調函數,很多人覺得函數都沒還搞明白,回調函數更暈菜了。其實可以通俗的理解指向函數的指針,本身是一個指針變數,只不過在初始化的時候指向了函數,這又回到了指針層面。沒搞明白指針再次深入的向前走特別難。

C語言的開發者們為後來的開發者做了一些省力氣的事情,他們編寫了大量代碼,將常見的基本功能都完成了,可以讓別人直接拿來使用。但是那麼多代碼,如何從中找到自己需要的呢?將所有代碼都拿來顯然是不太現實。

但是這些代碼,早已被早期的開發者們分門別類地放在了不同的文件中,並且每一段代碼都有唯一的名字。所以其實學習C語言並沒有那麼難,尤其是可以在動手鍛煉做項目中進行。使用代碼時,只要在對應的名字後面加上( )就可以。這樣的一段代碼就是函數,函數能夠獨立地完成某個功能,一次編寫完成後可以多次使用。

很多初學者可能都會把C語言中的函數和數學中的函數概念搞混淆。其實真相並沒有那麼復雜,C語言中的函數是有規律可循跡的,只要搞清楚了概念你會發現還挺有意思的。函數的英文名稱是 Function,對應翻譯過來的中文還有「功能」的意思。C語言中的函數也跟功能有著密切的關系。

我們來看一小段C語言代碼:

#include
int main()
puts("Hello World");
return 0;

把目光放在第4行代碼上,這行代碼會在顯示器上輸出「Hello World」。前面我們已經講過,puts 後面要帶(),字元串也要放在()中。

在C語言中,有的語句使用時不能帶括弧,有的語句必須帶括弧。帶括弧的就是函數(Function)。

C語言提供了很多功能,我們只需要一句簡單的代碼就能夠使用。但是這些功能的底層都比較復雜,通常是軟體和硬體的結合,還要要考慮很多細節和邊界,如果將這些功能都交給程序員去完成,那將極大增加程序員的學習成本,降低編程效率。

有了函數之後,C語言的編程效率就好像有了神器一樣,開發者們只需要隨時調用就可以了,像進程函數、操作函數、時間日期函數等都可以幫助我們直接實現C語言本身的功能。

C語言函數是可以重復使用的。

函數的一個明顯特徵就是使用時必須帶括弧(),必要的話,括弧中還可以包含待處理的數據。例如puts("果果小師弟")就使用了一段具有輸出功能的代碼,這段代碼的名字是 puts,"尚觀科技" 是要交給這段代碼處理的數據。使用函數在編程中有專業的稱呼,叫做函數調用(Function Call)。

如果函數需要處理多個數據,那麼它們之間使用逗號,分隔,例如:

pow(10, 2);

該函數用來求10的2次方。

好了,看到這里你有沒有覺得其實C語言函數還是比較有意思的,而且並沒有那麼復雜困難。以後再遇到菜鳥小白的時候,你一口一個C語言的函數,說不定就能當場引來無數膜拜的目光。

0x03 結構體、遞歸

很多在大學學習C語言的,很多課程都沒學完,結構體都沒學到,因為從章節的安排來看好像,結構體學習放在教材的後半部分了,弄得很多學生覺得結構體不重要,如果只是應付學校的考試,或者就是為了混個畢業證,的確學的意義不大。

如果想從事編程這個行業,對這個概念還不了解,基本上無法構造數據模型,沒有一個業務體是完全使用原生數據類型來完成的,很多高手在設計數據模型的時候,一般先把頭文件中的結構體數據整理出來。然後設計好功能函數的參數,以及名字,然後才真正開始寫c源碼

如果從節省空間考慮結構體裡面的數據放的順序不一樣在內存中佔用的空間也不一樣,結構體與結構體之間賦值,結構體存在指針那麼賦值要特別注意,需要進行深度的賦值。

遞歸一般用於從頭到位統計或者羅列一些數據,在使用的時候很多初學者都覺得別扭,怎麼還能自己調用自己?而且在使用的時候,一定設置好跳出的條件,不然無休止的進行下去,真就成無線死循環了。

對於結構體方面的知識,可以參見此前推送的文章《C語言結構體(struct)最全的講解(萬字干貨)》。具體也可以參見大佬的經驗:

相信大家對於結構體都不陌生。在此,分享出本人對C語言結構體的研究和學習的總結。如果你發現這個總結中有你以前所未掌握的,那本文也算是有點價值了。當然,水平有限,若發現不足之處懇請指出。代碼文件test.c我放在下面。在此,我會圍繞以下2個問題來分析和應用C語言結構體:


閱讀全文

與mdk編譯重復代碼相關的資料

熱點內容
怎麼能成為優秀程序員 瀏覽:245
智行app怎麼查學生認證 瀏覽:556
萬心pdf 瀏覽:92
哪個app能看3d電影 瀏覽:270
劍網三伺服器是怎麼運營 瀏覽:690
快手app快遞在哪裡查 瀏覽:474
開發聊天機器人python 瀏覽:856
程序員入職後無法工作 瀏覽:953
買海鮮用什麼app好 瀏覽:923
看劇用什麼app好 瀏覽:906
sql命令update 瀏覽:26
生意不忙怎麼解壓 瀏覽:501
歡太健康app在哪裡下載 瀏覽:489
androidtools使用教程 瀏覽:972
十天突破雅思口語pdf劍9 瀏覽:296
李誕笑場pdf 瀏覽:266
自用紙巾做解壓筆 瀏覽:130
銀行流水解壓碼是多少 瀏覽:896
百度哪個app好用 瀏覽:317
115廣告聯盟源碼 瀏覽:496