天天看點

【c++基礎系列】指針和引用          【c++基礎系列】指針和引用

          【c++基礎系列】指針和引用

   大家好,我是Lampard~~

   歡迎來到c++基礎系列的部落格

   前文再續,書接上一回。今天和大家講解一下c++中指針和引用的差別

   因為部落客我大學第一門課是學c,這也導緻了我産生一個很嚴重的誤區,指針就是引用。

   還記得當時的代碼是這樣的:

void add1(int num) {
    num = num + 1;
}

void add2(int* num) {
    *num = *num + 1;
}

int main () {
    int a = 0;
    int b = 0;
    add1(a);
    add2(&b);
    
    print(a);    // 結果為0
    print(b);    // 結果為1
}
           

當時老師告訴我們,第一種是傳值,第二種是傳引用,傳值不能改變原有變量,傳引用能夠改變原有變量。于是乎我就一直認為帶*号的都是能改邊原有變量的存在。

【c++基礎系列】指針和引用          【c++基礎系列】指針和引用

在c++,雖然記錄的都是對象的位址,但指針和引用指代的并不是同一個東西。

相同點:

  • 1). 都是位址的概念;
  • 2). 都是“指向”一塊記憶體。指針指向一塊記憶體,它的内容是所指記憶體的位址;而引用則是某塊記憶體的别名(我就是那一塊記憶體,我指我自己);
  • 3). 引用在内部實作其實是借助指針來實作的,一些場合下引用可以替代指針,比如作為函數形參。

不同點:

  • 1). 指針是一個實體(新增空間位址),而引用僅是個别名(建立多個引用都不會新增位址,因為都是同一位址的别名而已);
  • 2). 引用隻能在定義時被初始化一次,之後不可變;指針可變;引用“從一而終”,指針可以“見異思遷”;
  • 3). 引用不能為空,指針可以為空;
  • 4). “sizeof 引用”得到的是所指向的變量(對象)的大小,而“sizeof 指針”得到的是指針本身的大小;
  • 5). 指針和引用的自增(++)運算意義不一樣;
  • 6). 引用是類型安全的,而指針不是 (引用比指針多了類型檢查)
【c++基礎系列】指針和引用          【c++基礎系列】指針和引用

實際踩坑的例子QAQ:

【c++基礎系列】指針和引用          【c++基礎系列】指針和引用

當時我是想要實作這一道算法題,然後我寫下以下的代碼:

ListNode* mergeTwoLists(ListNode* l1, ListNode* l2) {
	ListNode* head = new ListNode();
	ListNode* curNode = head;
	while (l1 && l2) {
		ListNode* tmp = l1->val < l2->val ? l1 : l2;
		curNode->next = tmp;
		tmp = tmp->next;
		curNode = curNode->next;
	}
	curNode->next = l1 ? l1 : l2;
	return head->next;
}
           

我的思路是用tmp來記錄目前比較大的結點,然後把該結點的值連結到答案中後,讓tmp = tmp->next讓目前結點比較大的連結清單向下移動一個位置。但是問題就出現在這裡,因為我的tmp是指針類型,tmp = tmp->next并不能讓l1或者l2指向下一位置(引用才能做到這個功能),進而連結清單一直不往下走造成死循環。

ListNode* mergeTwoLists(ListNode* l1, ListNode* l2) {
	ListNode* head = new ListNode();
	ListNode* curNode = head;
	while (l1 && l2) {
		ListNode** tmp = l1->val < l2->val ? &l1 : &l2;
		curNode->next = *tmp;
		*tmp = (*tmp)->next;
		curNode = curNode->next;
	}
	curNode->next = l1 ? l1 : l2;
	return head->next;
}
           

 于是乎我修改代碼,把tmp改成**類型,變成了l1或者l2的引用,這樣子*tmp = (*tmp)->next;就可以讓連結清單移動一個結點,于是能實作功能,詳細的解題過程在以下的部落格中。

【算法百題之五十三】合并兩個有序連結清單

好,今天的分享就到這裡,祝各位功力漸長平步青雲,謝謝大家~~

繼續閱讀