指針和引用詳解---基礎篇

指針

  1. C++每個變量都有一個內存位置,每個內存位置都定義了一個可用&訪問的地址,表示在內存中的一個地址,&a表示變量a的地址
  2. 指針本身是一個對象(是一個變量),他的值是另一個變量的地址,指向一塊內存,指針存的是指向一塊內存的地址。指針分配內存空間,允許對指針的賦值和拷貝,指針在定義的時候不需要初始化(建議初始化)
int a = 20;//聲明一個實際變量
int *p;//聲明一個指針變量
p = &a;//把變量的地址賦給指針,就是在指針變量中存儲a的地址
cout << p << endl;//輸出指針變量中存儲的地址
cout << *p << endl;//訪問指針變量中地址指向的值,這裏就是20

給指針賦NULL是一個良好的編程習慣,int *a = NULL

  1. p++指針的遞增是指向下一個內存的位置,如果是int型下一個就是移動4個位置,如果是char型,下一個就是移動1個,
  2. 多級間接尋址,指向指針的指針,**
  3. 指向數組的指針,數組a[],*(a+4)是一個訪問a[4]的合法方式
  4. sizeof指針”得到的是指針本身的大小,而”sizeof引用”得到的是所指向的變量的大小
  5. 32位系統的指針是4字節,64位的是8字節

引用

  1. 引用是給已經存在的對象起了一個小名(也就是跟原來的對象就是一個東西),必須被初始化,定義引用的時候,就是將引用和初始值綁定在一起,一直綁定,而不是拷貝給引用,所以對引用的操作都是在綁定的對象上進行的,(引用本身不是對象,所以引用不能再被引用了),所以引用在初始化後就不能再被改變了,指針可以改變,可以先後指向不同的對象
  2. 因爲引用不是新創建的對象,所以引用不分配存儲空間,指針如果初始化需要分配存儲空間
  3. 引用與指針的區別,指針的值可以爲空,但是引用的值不能爲NULL,不存在空引用;一旦被初始化爲一個對象就不能指向另一個;引用必須在創建時被初始化
  4. 引用使用時無需解引用,指針需解引用
  5. 引用可以作爲參數傳遞,是實參的小名,如果不改變變量的值,通常採用常引用傳參
  6. 對引用自增自減是引用代表的對象的值發生變化,對指針自增自減是指針指向的位置發生變化
    賦值永遠改變的是等號左側的對象
int i = 42;
int &r = i;//r是一個引用,是i的小名
int *p;//p是一個指針
int *p1 = nullptr;//定義p1是一個空指針
int *p2 = &i;//這裏的&在等號右邊是取地址符,指針p2存放的是i的地址
*p2 = 0;//這裏的*是解引用符號,得到指針p2所指的對象,也就是經p2給i賦值,解引用操作僅適用於指向了某個對象的有效指針
p1 = &adc;//p1的值被改變,現在pi指向adc
*p1 = 0//*p1被改變,也就是指針pi指向的那個對象發生改變

函數引用傳參
引用和原始變量都指向同一個地址,因此通過引用修改原始變量中存儲的變量值,修改引用就是修改原始值;所以可以用於函數傳遞參數或函數返回值

函數引用傳參,將函數的形參指定爲引用,調用時就是把實參直接傳遞給形參,而不是拷貝給形參,所以在函數體中修改了形參,實參也會被修改
(補充一點:值傳遞只是簡單的拷貝,不會實現交換兩數的目的,因爲傳進去的是實參放的副本(副本啥意思,就是把實參的值拷貝一份然後傳進去),在交換函數內部執行的是形參的改變,形參的改變不會影響原來的實參)

swap(num1, num2);//引用傳遞
void swap(int &a, int &b){
    int temp = a;
    a = b;
    b = temp;}
//這種方式也是可以的,下面這個傳的是地址
swap(&num1, &num2);
void swap(int *a, int *b){
    int temp = *a;//這裏儘量不要把temp作爲指針,因爲沒有初始化很危險,當然你初始化了就是可以
    *a = *b;
    *b = temp;}

此文關於各種傳遞比較正確https://www.cnblogs.com/chen-kh/p/6696305.html
常引用:不希望通過引用來修改原始變量的值
const int &b = a;

紙上得來終覺淺,絕知此事要躬行,指針總是指來指去,還是上機看下到底怎麼指

#include <iostream>
using namespace std;

int main()
{
	int a[5] = {1,3,4,6,5};
	int *p = a;
	cout << p<<endl;//結果爲0x7ffeefbffde0
	cout <<*p<<endl;//結果爲1,因爲數組名a相當於數組的第一個元素
	p++;
	cout << p<<endl;//結果爲0x7ffeefbffde4,注意比剛剛的增加4,因爲一個int 是4,地址雖然執行的是+1,實際是+4
	cout << *p<<endl;//結果爲3,,自然就是第二個元素,因爲地址變了
	*p++;//執行完這個語句,*p向下指一位
	cout << p<<endl;//所以結果爲0x7ffeefbffde8,地址又增加了4
	cout << *p<<endl;//結果爲4,指向的內容自然隨着地址變化
	(*p)++;
	cout << p<<endl;//結果爲0x7ffeefbffde8。地址沒變,加的只是指向對象的值
	cout << *p<<endl;//結果爲5,這裏是剛剛的4+1
	*(p++);
	cout << p<<endl;//結果爲0x7ffeefbffdec,地址又增加了
	cout << *p<<endl;//結果爲6,指向的內容變化了
   return 0;
}

我想通過博客幫助和我一樣有困惑的小夥伴,看完此文你懂了嗎,歡迎一起交流,博客僅爲我個人的學習筆記,如有錯誤,歡迎指正

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