一、引用
1、引用的定義
引用是C++中的一個很重要的概念,引用不是新定義了一個變量,而是給已經存在的變量取了一個別名,實際上編譯器並不會爲它分配新的內存空間,它和它所引用的變量使用同一塊命名空間。
其語法爲:類型& 引用變量名(對象名) = 引用實體;
void TestFun() {
int a = 10;
int& ra = a;
cout << a << endl;
cout << ra << endl;
cout << &a << endl;
cout << &ra << endl;
}
int main() {
TestFun();
return 0;
}
由此可見 ,二者的值是相同的,地址也是相同的!!!
2、引用的特性
1、引用在定義的時候必須進行初始化;
2、一個變量可以有多個引用;
3、引用一旦擁有一個實體之後,就不能在引用別的其他實體;
void TestFun(){
int a = 10;
//int ra&; //這句話是錯誤的!引用定義時必須進行初始化
int& rra = a;
int& rrra = a;
}
3、常引用
//常引用
void TestFun() {
const int a = 10;
//int& ra = a;
const int& ra = a;
}
4、引用的使用場景
1、做參數
//引用作爲參數
void Swap(int& a,int& b) {
int temp = a;
a = b;
b = temp;
}
2、做返回值
int& TesrFun1(int& a) {
a += 10;
return a;
}
3、一段有意思的代碼!!!
int& Add(int a,int b) {
int c = a + b;
return c;
}
int main() {
int& ret = Add(1,2);
Add(3, 4);
cout << ret << endl;
system("pause");
return 0;
}
結果等於 7 !!! 而不是 3 !!!
詳情參考:https://blog.csdn.net/qq_40550018/article/details/81225519
注意:如果函數返回時,離開函數作用域後,其棧上空間已經還給系統,因此不能用棧上的空間作爲引用類型返回。如果以引用類型返回,返回值的聲明週期必須不受函數的限制(即比函數生命週期長);
5、引用和指針的區別
- 引用在定義的必須初始化,指針沒有要求;
- 引用在初始化引用一個實體之後,就不能在引用第二個實體,而指針可以在任何時候指向任何一個同類型的實體;
- 沒有NULL引用,但是有NULL指針;
- 在sizeof中含義不同:引用結果爲所引用的實體類型的大小,但是指針始終是地址空間所佔字節個數(32位系統下佔4個字節);
- 引用自增加即引用的實體自增加,指針則是在原指針所指向的位置向後偏移一個位置;
- 有多級指針,但是沒有多級引用;
- 訪問實體的方式不同,指針需要顯示解引用,引用則由編譯器自行處理;
- 引用比指針使用起來相對安全;
二、內聯函數
在C++中以inline修飾的函數叫做內聯函數,編譯時C++編譯器會在調用內聯函數的地方展開,沒有函數壓棧的開銷,屬於一種以空間換時間的當時,提升了程序允許的效率;
注意:因爲內聯函數是在函數調用的地方進行展開,以空間換時間,所以代碼很長或者有循環/遞歸的函數不適宜使用內聯函數。當然這種情況,編譯器有的時候也會進行自動優化,比如如果定義位inline的函數體內有循環/遞歸等,編譯器優化時會忽略掉內聯。
三、auto關鍵字(C++11)
auto這個關鍵字在早期的版本中:使用auto修飾的變量,都是具有自動存儲功能的局部變量;
C++11:auto不再是一個存儲類指示符,而是作爲一個新的類型指示符來指示編譯器,auto聲明的變量必須由編譯器在編譯時期推導而得。
我們看一段代碼就可以直到,auto的神奇用法:
int Test() {
return 10;
}
int main() {
int a = 10;
auto b = a;
auto c = 'a';
auto d = Test();
cout << typeid(b).name() << endl;
cout << typeid(c).name() << endl;
cout << typeid(d).name() << endl;
return 0;
}
但是auto也有幾個非常值得注意的地方:
- auto在定義變量的時候必須對其進行初始化,auto他並非是一種“類型”的聲明,而是一個佔位符,編譯器會在編譯期間把他替換成變量的實際類型;
- auto不能作爲函數的參數使用,因爲編譯器無法對函數參數的實際類型進行推導;0
四、基於範圍的for循環(C++11)
for循環後的括號由冒號“:”分爲兩個部分:第一部分是範圍內用於迭代的變量,第二部分則表示被迭代的範圍;
int main() {
//遍歷一個數組
int array[] = {1,2,3,4,5,6,7,8,9};
for (auto e : array)
cout << e << "";
cout << endl;
system("pause");
return 0;
}