一文詳解C++中的引用與關(guān)鍵字auto
一.引用
1.引用的概念
引用就是給一個已經(jīng)存在的變量取一個別名,與變量共用一段內(nèi)存空間。注意引用的類型必須和變量類型相同,來演示下引用如何使用。
#include <iostream> using namespace std; int main() { int a = 1; int& b = a; int& c = b; int& d = c; cout << &a << endl; cout << &b << endl; cout << &c << endl; cout << &d << endl; return 0; }
如上面的代碼所示:我們給a取了個別名b,給b取別名c…也就是b是a的引用,c是b的引用…。其實b,c,d都代表著a,它們都共用著一塊內(nèi)存空間。
如下圖所示:
2.引用的使用和問題
引用的注意事項:
- 引用必須初始化
- 引用不能更改
- 一個變量可以有多個引用
引用可以作為函數(shù)的參數(shù)也可以做返回值,在之前學(xué)習(xí)C語言我們常使用指針傳參,也就是傳址調(diào)用來改變外部變量的值。學(xué)習(xí)引用后,我們只用引用傳參就會特別方便。
當(dāng)返回引用時,就會引出很多問題,這里我們來解析下下面的代碼:
int& Add() { int n = 0;//靜態(tài)變量static int a = 0; n++; return n; } int main() { int ret=Add(); cout << ret << endl; return 0; }
n在Add函數(shù)中變?yōu)?,Add返回了n的引用,我們用變量ret來接收n的引用也就是n的值,但是有個問題就是——n在出Add函數(shù)后,函數(shù)棧幀如果被清理的話,函數(shù)返回引用找到的值就會是隨機(jī)值。如果棧幀沒有被清理,那ret僥幸是正確的1。為了避免這種情況我們可以將Add函數(shù)的n設(shè)為靜態(tài)變量。
為了驗證,我們再看一下面的代碼:
int& Add(int x) { int n = x; n++; return n; } int main() { int& ret=Add(10); cout << ret << endl; Add(20); rand(); cout << ret << endl; return 0; }
假設(shè)出Add函數(shù)后棧幀不破壞那打印結(jié)果就是11\n21,但是我們調(diào)用個函數(shù),模擬函數(shù)棧幀破壞的情況,那結(jié)果是不是像我們預(yù)想的那樣為隨機(jī)值呢。
總結(jié)
引用傳參適合大部分的情況
將引用返回值時需要注意引用對象還是否出函數(shù)是否還存在。
下面我們來看引用使用場景及其優(yōu)點:
1.引用做參數(shù)-(輸出型參數(shù))
2.引用做參數(shù)-(減少拷貝提高效率) (大對象/深拷貝類對象)
3.引用做返回值-(減少拷貝提高效率) (大對象/深拷貝類對象)
4.引用做返回值-修改返回值+獲取返回值
接下來再講一下常引用、引用權(quán)限的放大、縮小、平移:
int func() { stctic int a=0; a++; return a; } int main() { //引用的權(quán)限可以平移和縮小不可以放大 int a = 0; int& b = a;//平移 const int& c = a;//縮小 ++a; ++c;//放大 const int a = 10; int& b = a;//只能給變量取別名 double c = 3.14; int& d = c;//引用的類型需要匹配 const int& e = c;//類型轉(zhuǎn)換會創(chuàng)建臨時變量 臨時變量具有常量性質(zhì) int& ret=func();//權(quán)限放大 return 0; }
語法層面上引用不會開空間知識對變量取得一個別名,而從底層匯編指令來看的話引用是類似指針的方式使用的。
3.引用與指針的比較
引用和指針有許多不同點:
- 引用需要初始化,指針不要求
- 引用不能修改,指針可以
- 有空指針,沒有空引用
- 引用更為安全,指針可能出現(xiàn)野指針和越界等情況
- 在sizeof中引用是類型的字節(jié)大小,指針是根據(jù)機(jī)器位數(shù)來判斷字節(jié)個數(shù)
- 引用在語法上定義一個變量的別名,指針儲存一個變量的地址
- 有多級指針沒有多級引用
- 指針需要根據(jù)地址解引用訪問,引用是編譯器自己處理的
二.關(guān)鍵字auto
auto可以自動識別類型,當(dāng)類型過于復(fù)雜冗長時,auto使用起來非常的方便。
int main() { int a = 1; auto b = 10; auto c = 3.14; }
在同一行定義多個變量時,需要注意同一行的變量類型要一致,不然auto無法正確識別:
int main() { auto a = 1, b = 2; auto c = 3, d = 4.0;//類型不同 }
auto還不能作為函數(shù)的參數(shù)以及定義數(shù)組
auto還有個重要的應(yīng)用——范圍for循環(huán)
他提供了一種更簡便的for遍歷的方法根據(jù)冒號”:”分為兩部分:第一部分是范圍內(nèi)用于迭代的變量,第二部分則表示迭代的范圍。
int main() { int arr[] = { 0,1,2,3,4,5,6 }; for (auto x : arr) cout << x << endl; }
以上就是一文詳解C++中的引用與關(guān)鍵字auto的詳細(xì)內(nèi)容,更多關(guān)于C++引用與關(guān)鍵字auto的資料請關(guān)注腳本之家其它相關(guān)文章!
相關(guān)文章
C++函數(shù)三種傳參形式(指針傳遞、引用傳遞、值傳遞)
不論是哪種參數(shù)傳遞方式,都有形參和實參之分,本文主要介紹了C++函數(shù)三種傳參形式(指針傳遞、引用傳遞、值傳遞),具有一定的參考價值,感興趣的可以了解一下2024-03-03Linux系統(tǒng)下如何使用C++解析json文件詳解
JSON(JavaScript Object Notation, JS 對象簡譜) 是一種輕量級的數(shù)據(jù)交換格式。下面這篇文章主要給大家介紹了關(guān)于Linux系統(tǒng)下如何使用C++解析json文件的相關(guān)資料,需要的朋友可以參考下2021-06-06C++中的局部變量、全局變量、局部靜態(tài)變量、全局靜態(tài)變量的區(qū)別
本文主要介紹了C++中的局部變量、全局變量、局部靜態(tài)變量、全局靜態(tài)變量的區(qū)別。具有很好的參考價值,下面跟著小編一起來看下吧2017-02-02