在實驗中觀察指標 C 函式引數的壓棧順序

2022-09-08 22:33:30 字數 1221 閱讀 8137

好久沒寫東西了,突發奇想,寫寫函式引數的壓棧順序

先看看這個問題

然後看我簡化的**,猜輸出結果是多少?

#includeusing namespace std;

int main()

根據++和--的特性,i++的時候數值不變,輸出0,i--時i才加上1,輸出1。

事實是這樣嗎?我在多台編譯器上執行,輸出的結果都是:

-1 0

根據我之前寫過的指標篇的內容,函式的區域性變數儲存在棧中,都是獨立的,引數同樣儲存在棧中,才導致了swap函式改變函式引數必須使用指標。

那麼,函式引數,在棧中是如何排列的呢?順序?倒序?

我們寫乙個簡短的**,來實驗一下。

#includeusing namespace std;

void test(int a,int b)

int main()

由於是位址,不同編譯器的結果不同。但肯定的是,a比b大4。

如果多加幾個變數進去,我們發現,位址的大小從大到小遞減。

圖源:《征服c指標》

從這張圖中可以看出,c語言中,引數是從後往前堆積在棧中的。這種處理方式的好處在於,無論有多少個引數,總能找到第乙個引數的位址,這樣就可以順次找到後面的引數。否則,從後往前,就無法找到第乙個引數,也無法實現可變長引數的功能。

例如在printf中,我們找到第乙個引數的位置,例如"%d %s",就可以順次解析後面的位址的引數,因為引數是連續在記憶體排列的。

既然引數是從後往前放入棧中的,那麼,我們就可以解釋這個問題了。

#includeusing namespace std;

int main()

開頭的**。如果編譯成組合語言進行執行,應該是這個樣子(如果有錯誤請指正,手寫的)

sub [i],1 ;i--

push [i]

add [i],1 ;i++

push [i]

push offset string "%d %d" ;"%d %d"

call dword ptr_printf ;呼叫printf

c函式程式設計之指標引數和指向指標的指標引數

我們給出兩個函式如下 void getmem1 char p void getmem2 char p int main 為什麼會這樣呢?其實這個問題理解起來有點繞,關鍵是理解變數作函式形參呼叫的時候都是要分配乙個副本,不管是傳值還是傳址。當我們使用getmem1的時候,str是乙個指標,我們建立了臨...

C 指標作函式引數的情況

指標作為函式引數,扮演的是值傳遞還是位址傳遞的角色,要看指標變數在函式裡面是如何被使用。1 如果對其使用取位址符號 則是位址傳遞。意味著你要操縱傳過來的位址所指向的值。2 如果直接使用變數名,則是值傳遞。意味著你所改變的,只不過是所宣告的那個區域性變數的值。扮演什麼角色和如何傳進來值是沒什麼關係的。...

C 指標作為函式引數的問題

其實,對於c 或者c 最難的一塊地方估計就是指標了。指標是強大的,但也是很多人載在這裡的地方。前段時間寫了一篇文章 c 之 陣列與指標的異同 對c 和c 中的指標做了乙個初步的講解。這次將講解一下指標作為函式引數傳遞的問題。很多人對於指標的使用是有所了解的,但還是經常會載在指標的問題上,是因為還不夠...