【C++自學筆記】從C到C++入門級的小知識(引用、內聯函數、auto關鍵字、範圍for循環)

一、引用

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;
}

 

發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章