天天看點

怎麼輸出函數的傳回值_C++ 函數:引用參數,傳參機制

@all 原創連載,喜歡點關注。

12. 引用參數與傳參機制

怎麼輸出函數的傳回值_C++ 函數:引用參數,傳參機制

12.1 引用變量

當我們聲明一個新變量時,總會給這個變量取一個好聽的名字。其實變量的名字并不是唯一的,你可以給變量起令一個别名。建立變量的别名可以通過聲明一個引用變量來完成。

怎麼輸出函數的傳回值_C++ 函數:引用參數,傳參機制

上圖中第15行建立了一個引用變量DPA,變量DPA(Damage per attack)就是變量damage的一個别名。

初始化引用變量必須這樣做:用一個已經存在的變量來初始化引用變量。這樣的話我們就明白了:引用變量實際上指向的是用來初始化的那個舊變量。

怎麼輸出函數的傳回值_C++ 函數:引用參數,傳參機制

上圖中第22行我們讓DPA的值增加10,然後輸出damage變量的值,結果發現damage的值變為了110.f。是以修改引用變量的值等同于修改變量的值。

12.2 引用參數

引用變量有哪些用處呢?

引用變量可以作為函數的參數來使用。

怎麼輸出函數的傳回值_C++ 函數:引用參數,傳參機制

上圖中的兩個函數的參數都是引用類型的參數,引用參數隻需要在函數聲明中給變量前加上&符号就行。使用引用參數的函數實作寫法和函數調用方式與使用非引用參數的函數并無差異。

但是,值得一提的是,函數僅僅由參數的引用與非引用構成的重載常常導緻調用函數時二義性編譯錯誤。

怎麼輸出函數的傳回值_C++ 函數:引用參數,傳參機制

上圖中我們定義了兩個交換函數,引用參數與非引用參數讓這兩個函數構成了重載,但是在main函數中使用函數時,産生了錯誤,因為編譯器無法确定你是想使用哪個函數版本。是以在函數中要避免這樣引用與非引用形成的重載。

12.3 傳回引用值

函數的傳回值也可以是一個引用類型。

怎麼輸出函數的傳回值_C++ 函數:引用參數,傳參機制

上圖中函數的傳回值聲明為引用類型,在這個函數中傳回值即為數組中元素的别名。

傳回引用時特别要注意的是:不要傳回局部變量的引用,這是不安全的。

怎麼輸出函數的傳回值_C++ 函數:引用參數,傳參機制

12.4 函數傳參機制

1.按值傳遞參數

函數傳遞參數的方式不同對參數資料有不同的影響。

函數在傳遞參數時,預設采用按值傳遞參數機制:把要傳入的資料複制了一份并把複制品傳遞給函數。

怎麼輸出函數的傳回值_C++ 函數:引用參數,傳參機制

上圖中的運作結果我們看到函數裡面a的值為2,函數外面a的值并沒有改變,依然是1。

按值傳遞參數機制很好的保護了源資料,防止函數内部試圖對用作參數的資料的修改,畢竟源資料是不希望以這樣的方式被修改的。

2.按引用傳遞參數

如果我們把函數的參數改為引用類型,那上圖中這個例子的答案會不一樣嗎?

怎麼輸出函數的傳回值_C++ 函數:引用參數,傳參機制

依然是同一個函數,差别是函數的第一個參數的類型聲明為引用類型,運作後你會發現函數内外輸出的值都為2。這是因為函數參數聲明為引用類型時,就不再拷貝參數了,而直接把源變量傳遞給函數,這樣在函數内部對引用參數的修改對源變量是有效的。

3.按常量引用傳遞參數

按值傳遞參數機制,能夠保護源資料,但是變量的複制操作降低了性能;按引用傳遞參數機制,不存在參數的複制操作不增加性能的開銷,但是産生了資料不安全問題。

在設計函數時如果既想要按值傳遞參數的安全性,又想保留引用參數的高效性,C++能否做到呢?可以,用常量引用類型參數。

怎麼輸出函數的傳回值_C++ 函數:引用參數,傳參機制

上圖中把函數的形參a聲明為const int&類型,運作函數後兩次輸出結果都為1。

在函數中形參a聲明為const, 表明這個參數a在函數體中是不允許被修改的。如果一個函數的形參聲明為聲明為const &類型,既高效又安全,兩全其美。怎麼樣,你是否也嘗試這樣的函數聲明方式呢?