最近寫二叉樹的資料結構實驗,想用乙個沒有返回值的函式來建立乙個樹,發現這個樹就是建立不起來,那麼我就用這個例子討論一下c語言中指標作為形參的函式中傳遞中隱藏的東西。
大家知道c++中有引用的概念,兩個資料引用同乙個資料,那麼更改任意的乙個都相當於更改了本體,那麼另乙個資料所對應的值也會改變,可是c中是沒有這個概念的。所以就產生了一些東西。和我們本來想的有差別。
一、明確c語言中函式的入口:
c語言中函式的形參負責接收外部資料,那麼資料究竟怎麼進入函式的呢,其實我們在函式體內操作的形參只是傳遞進來引數的乙個副本,也就是說這兩個引數雖然名字一樣,對應的值一樣,但是他們兩個對應的記憶體位址是不一樣的,也就是說這就是兩個「看上去一模一樣」的完全不同的變數。
所以一定要知道,c語言中函式是值傳遞的,也就是說,c語言只能把值傳給函式,而不能把你想要傳遞的變數完全的放進函式內部。
二、指標傳遞給函式:
指標作為乙個特殊的東西,他的強大之處就在於指標可以直接修改記憶體位址上的資料。雖然指標特別強大,但是他也難逃函式的限制,你傳遞給函式乙個指標,因為是值傳遞,那麼你在函式體內的使用的形參指標也只是乙個副本,只是乙個指向的值和你傳進來的那個指標一樣的乙個另外的乙個變數。也就是說他和普通常量是沒有區別的。
三、我想要達到引用的效果怎麼實現
c語言中因為是值傳遞的,那麼我們就傳遞值,只要講想要傳遞進函式的東西的位址傳進函式,並且函式用乙個指標接收,那麼就相當於把這個變數位址原封不動的傳遞給了函式,形參的指標指向的是外面傳進來的位址,有了位址不就好辦了嗎。
四、下面是我寫的乙個二叉樹建立的乙個無返回值的版本:
因為二叉樹是用遞迴建立的,就像建立鍊錶一樣,乙個節點乙個節點建立,如果不獲得上乙個節點的位址,你怎麼把鍊錶連線起來呢,鍊錶就散開了。
所以只能通過傳遞位址來達到找到已經建好的鍊錶的前驅,才能把各個節點穿起來。
#include #include typedef struct tree tree;
void inittree(tree **t)
else
}void qiant(tree *t)
}int main (void)
注意看樹的建立那個函式,我每次都是穿進去乙個節點的位址,然後通過位址來找到已經建立好的樹,才能將樹建立起來。那麼有的人會問了?為什麼不是下面這個寫法呢?
void inittree(tree *t)
else
}
這種寫法,你每次傳進來的都是乙個變數,說過,c語言是值傳遞的,那麼每次你申請的節點空間都是給副本申請的,然後遞迴的是副本的左右孩子,也就是說你的樹根本沒有建立起來,因為每次申請的記憶體都沒有連線上。
為什麼我的那個寫法可以呢,因為我是用乙個指向指標的指標來存位址的,我給傳進來的位址申請了記憶體,也就相當於給穿進來的那個節點本身申請了記憶體,而不是給副本,所以二叉樹就順其自然建立起來了。
最後記住,c語言是值傳遞的,任何東西傳遞給函式的都只是值!
c語言和 語言中函式引數的傳遞
在呼叫乙個函式時進行引數傳遞 不只是講引數列表裡的引數,包括函式返回值的引數傳遞 其本質上進行的工作都是一樣的,即使用實參初始化形參。實參與形參本質上是兩個完全不同的變數,它們之間並沒有更深入的聯絡,僅僅只是變數與初始值的關係而已。很普通的那種,大家都了解的差不多。在此處需要強調一下,所謂傳值,其實...
C語言中的引數傳遞
問 你認為這個函式是在做什麼呀?答 好像是對引數 x,y的值對調吧?請往下看,我想利用這個函式來完成對a,b兩個變數值的對調,程式如下 void main 我問 exchg1 裡頭的 printf x d,y d n x,y 語句會輸出什麼啊?我再問 exchg1 後的 printf a d,b d...
C語言中給main函式傳遞引數!
相信大家用c語言定義main函式時,大多數人的寫法都是int main void 其實main函式是可以向其傳遞引數的,給個例項 給main函式傳參例項 include include int main int argc,char argv int main int argc,char argv i...