c語言引用傳遞技巧 c語言函數(shù)調(diào)用規(guī)則?
c語言函數(shù)調(diào)用規(guī)則?在參數(shù)訊息傳遞中,有兩個重要的問題需要要明確只能證明:1.當(dāng)參數(shù)個數(shù)緩于一個時,聽從什么順序把參數(shù)壓入內(nèi)存緩沖區(qū);2.函數(shù)調(diào)用后,由誰來把內(nèi)存池恢復(fù)原狀。在高級語言中,應(yīng)該是實際函
c語言函數(shù)調(diào)用規(guī)則?
在參數(shù)訊息傳遞中,有兩個重要的問題需要要明確只能證明:
1.當(dāng)參數(shù)個數(shù)緩于一個時,聽從什么順序把參數(shù)壓入內(nèi)存緩沖區(qū);
2.函數(shù)調(diào)用后,由誰來把內(nèi)存池恢復(fù)原狀。
在高級語言中,應(yīng)該是實際函數(shù)的全局函數(shù)來只能證明這兩個問題的。比較普遍的全局函數(shù)有:
stdcallcdeclfastcallthiscallthiscallnakedcall
下面就共有詳細(xì)介紹這幾種內(nèi)部函數(shù)
stdcall動態(tài)鏈接庫又被一般稱Pascal動態(tài)創(chuàng)建。在MicrosoftC系列的C/C編譯器中,使用PASCAL宏,WINAPI宏和CALLBACK宏來更改函數(shù)的動態(tài)創(chuàng)建為stdcall。
stdcall內(nèi)部函數(shù)的函數(shù)聲明為:
int_stdcallfunction(inta,int b)
stdcall的動態(tài)鏈接庫那樣的話:
(1)參數(shù)從右往左第二次壓入內(nèi)存池
(2)由被調(diào)用函數(shù)自己來恢復(fù)內(nèi)存緩沖區(qū)
(3)函數(shù)名不自動加前導(dǎo)下劃線,后面緊跟著走一個@,數(shù)日后緊領(lǐng)著參數(shù)的尺寸
上面那個函數(shù)英文翻譯成匯編語言將轉(zhuǎn)成:
pushb先壓入第二個參數(shù)
pusha再壓入最先參數(shù)
callfunction調(diào)用函數(shù)
在編譯時,此函數(shù)的名字被漢語翻譯為
cdecl全局函數(shù)又稱作C內(nèi)部函數(shù),是C語言缺省的動態(tài)鏈接庫,它的語法為:
intfunction(inta,int b)//未經(jīng)修飾符應(yīng)該是C全局函數(shù)
int_cdeclfunction(inta,int b)//必須明確指定用C動態(tài)創(chuàng)建
cdecl的動態(tài)創(chuàng)建做出決定了:
(1)參數(shù)從右往左排列壓入堆棧
(2)由動態(tài)鏈接庫者復(fù)原內(nèi)存池
(3)函數(shù)名不自動加前導(dǎo)下劃線
的原因是由動態(tài)創(chuàng)建者來可以恢復(fù)內(nèi)存緩沖區(qū),并且C內(nèi)部函數(shù)不能函數(shù)的參數(shù)個數(shù)是不固定不動的,這是C語言的一大特色。
此的函數(shù)被翻譯為:
pushb//先壓入第二個參數(shù)
pusha//在壓入第一個參數(shù)
callfuntion//調(diào)用函數(shù)
addesp,8//需要清理邏輯塊
在編譯時,此的函數(shù)被翻譯成成:_function
fastcall遵循名字上表述就可以很清楚,它是一種迅速全局函數(shù)。此的函數(shù)的第一個和第二個DWORD參數(shù)實際ecx和edx傳遞,
后面的參數(shù)從右到左的順序壓入棧。
被調(diào)用函數(shù)定期清理堆棧。
函數(shù)名修個規(guī)則同stdcall
其聲明聲明語法為:
intfastcallfunction(inta,int b)
thiscall動態(tài)創(chuàng)建是僅有一種沒法顯示重新指定的修飾符。它是c類成員函數(shù)缺省的調(diào)用。因此成員函數(shù)調(diào)用另外一個this指針,但必須用這種特殊的方法的內(nèi)部函數(shù)。
thiscall動態(tài)鏈接庫換句話說:
參數(shù)從右到左壓入棧。
如果沒有參數(shù)個數(shù)可以確定,this指針通過ecx訊息傳遞給被調(diào)用者;如果沒有參數(shù)個數(shù)不確認(rèn),this指針在所有參數(shù)壓入棧后被壓入棧。
參數(shù)個數(shù)只怕的,由全局函數(shù)者清理內(nèi)存映射,否則不由函數(shù)自己定期清理堆棧。
可以看見,對此參數(shù)個數(shù)固定不動的情況,它傳說中的stdcall,不定時則像cdecl。
是一種都很極少見的調(diào)用,一般初級程序設(shè)計語言中不常見。
函數(shù)的聲明內(nèi)部函數(shù)和實際中內(nèi)部函數(shù)要一致,必然會編譯器會才能產(chǎn)生混亂。
函數(shù)名字如何修改規(guī)則:
1.C編譯器時函數(shù)名修飾修飾約定規(guī)則:
__stdcall動態(tài)創(chuàng)建約定在控制輸出函數(shù)名前而且一個下劃線前綴,后面另外一個“@”符號和其參數(shù)的字節(jié)數(shù),格式為。
__cdecl內(nèi)部函數(shù)約定僅在輸出低函數(shù)名前再加一個下劃線前綴,格式為_function。
__fastcall動態(tài)創(chuàng)建約定在控制輸出函數(shù)名前再加一個“@”符號,后面也一個“@”符號和其參數(shù)的字節(jié)數(shù),格式為@。
它們均不轉(zhuǎn)變輸出來函數(shù)名中的字符大小寫,這和PASCAL動態(tài)鏈接庫約定完全不同,PASCAL雙方約定輸出的函數(shù)名無任何修飾且全部字母。
2.C程序編譯時函數(shù)名稍微修飾約定規(guī)則:
__stdcall調(diào)用約定:
(1)以“?”標(biāo)示函數(shù)名的開始,后跟函數(shù)名;
(2)函數(shù)名后面以“@@YG”標(biāo)有參數(shù)表的開始,后跟參數(shù)表;
(3)參數(shù)表以代號表示:
X--void,
D--char,
E--unsignedchar,
F--shorter,
H--int,
I--unsignedint,
J--shorter,
K--unsignedlong,
M--float,
N--slip,
_N--bool,
....
PA--意思是指針,后面的代號并且指針類型,如果沒有是一樣的類型的指針在不出現(xiàn),以“0”不用,一個“0”代
表兩次亂詞;
(4)參數(shù)表的第一項為該函數(shù)的返回值類型,不數(shù)日左面為參數(shù)的數(shù)據(jù)類型,指針標(biāo)識在其所指數(shù)據(jù)類型前;
(5)參數(shù)表后以“@Z”標(biāo)志整個名字的結(jié)束,如果沒有該函數(shù)無參數(shù),則以“Z”標(biāo)識結(jié)束后。
其格式為“?functionname@@YG*****@Z”或“?functionname@@YG*XZ”,比如
intTest1(char*var1,size_tlittle)-----“?Test1@@”
voidTest2()-----“?Test2@@YGXXZ”
__cdecl調(diào)用約定:
規(guī)則同上面的_stdcall動態(tài)創(chuàng)建約定,只不過是參數(shù)表的開始標(biāo)識由上面的“@@YG”轉(zhuǎn)換成“@@YA”。
__fastcall動態(tài)鏈接庫約定:
規(guī)則同上面的_stdcall調(diào)用約定,只不過參數(shù)表的開始標(biāo)識由上面的“@@YG” “@@YI”。
VC對函數(shù)的省缺聲明是#34__cedcl#34,將只能被C/C調(diào)用。
2. C語言規(guī)定:在一個源程序中,main函數(shù)的位置( )。A)必須在最開始B)必須在系統(tǒng)調(diào)用的庫函數(shù)的后面C?
按你這選項應(yīng)該是B了,,不一定得在最前,經(jīng)常我的main()還在子函數(shù)的后面呢