C/C++ 函數參數傳遞:傳值,傳指針,傳引用

前面咱們介紹了函數的調用約定,明白了函數調用者與被調用者之間傳遞參數的順序與如何進行棧恢復的。 實際上,函數調用者如何將參數傳遞給被調用者也是有講究的。 總的來講,函數參數傳遞分爲3種狀況:傳值,傳指針和傳引用。

首先,理解一下實參與形參的概念。
int func(int x)//x是形參
{
    return x*x;
}
int main(void)
{
    int a = 10;
    func(a);//a是實參
    return 0;

上面的代碼中,x是形參,a是實參。形參x是實參a的一個拷貝。

安全

一,傳值

所謂傳值,顧名思義,就是把實參的值直接傳遞給函數。由於形參是實參的拷貝,因此傳值沒法改變實參。在C++裏面,若是傳遞的是對象, 那麼,在傳值過程當中,還會隱式的調用對象的拷貝構造函數,有必定的計算執行開銷(至關於建立了一個臨時對象,函數調用完成後執行臨時對象的析構函數)。
void func(int x)//func採用了傳值的形式
{
    x = x+1;
    printf("x=%d\n", x);
}
int main(void)
{
    int a = 0;
    func(a);//傳值不能修改a的值
    printf("a=%d\n", a);
    return 0;
}
分析:上面的程序採用了傳值的參數傳遞形式,把a的值0傳遞給了func函數,而因爲x是a的一個拷貝,所以,x=x+1值修改了x的值 並無修改a的值。因此上面程序執行的結果,輸出爲:
x=1
a=0函數

二,傳指針

傳指針就是把實參的地址傳遞給函數。傳指針能夠修改實參的值,在C++裏也不會存在調用對象的拷貝構造函數的問題, 傳指針的效率比傳值要高。因此,若是須要修改實參的值,就不能傳值,而須要傳指針等。
可是,傳指針比傳值複雜,指針計算一旦移動出了正常範圍,會形成程序的非法訪問等。
void func(int *x)//func採用了傳指針的形式
{
    *x = *x+1;
    printf("*x=%d\n", *x);
}
int main(void)
{
    int a = 0;
    func(&a);//把實參a的地址傳遞給了函數func
    printf("a=%d\n", a);
    return 0;
}
分析:傳指針能夠修改實參的值。根據指針的定義,*x就是a,因此,*x=*x+1,即爲a = a+1,因此上面的代碼輸出結果爲:
*x=1
a=1指針

三,傳引用


所謂引用其實就是變量的一個別名。傳引用是C++裏面引入的一種參數傳遞方法。傳引用實際上也是傳遞的實參的指針,因此可以修改實參的值。 可是,引用的特性告訴咱們,一旦引用初始化後,這個引用就不能再改變。因此,傳遞引用其實是擁有傳值的方便簡單,也同時 具有了傳指針的高效,又沒傳指針的危險,相對安全。

void func(int &x)//func採用了傳引用的形式
{
    x = x+1;
    printf("x=%d\n", x);
}
int main(void)
{
    int a = 0;
    func(a);//把實參a的引用傳遞給了函數func
    printf("a=%d\n", a);
    return 0;
}
分析:func採用傳引用的方法定義,實參a引用傳遞給函數func以後,func可以修改實參的值。因此上面的程序執行結果爲:
x=1
a=1
總之:傳值不能修改實參,且若是是對象,效率較低;傳指針可以修改實參,效率較高,但容易出錯;傳引用可以修改實參,效率較高,並且不易出錯。對象

相關文章
相關標籤/搜索