C++(9)--裸指針、智能指針、引用

指針

  • 1.裸指針的基本概念
    • 1.1 裸指針的聲明*/初始化&
    • 1.2 操作裸指針--間接運算符*
    • 1.3 裸指針使用 demo--指向一個簡單變量
    • 1.4 空指針--nullptr
    • 1.5 特殊指針--void *ptr
  • 2.指針和引用--引用定義&
  • 3.指針和數組
    • 3.1 數組指針的定義
    • 3.2 數組指針遞增/遞減操作
    • 3.3 指針與數組使用的一些注意點

《老九學堂C++課程》《C++ primer》學習筆記。《老九學堂C++課程》詳情請到B站搜索《老九零基礎學編程C++入門》
-------------簡單的事情重復做,重復的事情用心做,用心的事情堅持做(老九君)---------------

1.裸指針的基本概念

指針是一個值為內存地址的變量(數據對象)。也就是說指針它一樣是一個變量,只不過該變量中存放的是另一個對象的內存地址,存放另一個對象的地址的操作又叫指向了該對象。
裸指針相對于智能指針而言,智能指針的使用詳見part 5

  1. 變量名–地址的助記符, 指針–存放內存地址

  2. 定義指針時不賦初值,該指針叫野指針。強烈建議初始化所有指針/盡量等定義了變量之后再定義指向它的指針.

  3. 指針指向的對象可以改變(可以通過賦值–去地址符號改變指針的內容)

  4. 指針類型與指向對象的類型匹配

  5. 裸指針需要手動釋放,否則會造成內存泄漏

1.1 裸指針的聲明*/初始化&

裸指針聲明 --僅聲明不初始化的指針是非常不安全的,所以推薦聲明完就初始化。

數據類型 * 指針變量名     // 定義一個指向(數據類型)變量的指針
int *ptr_num;
int *ptr_name;
int *money_ptr;
double *p_price;

注意:星號靠前靠后都是定義指針型變量,建議靠后結合知名該變量是指針。

int* a,b,c; //只有a為指向int 類型變量的指針,b、c是一般的int 型變量
int *a, *b, *c; //定義了3個指向int 類型變量的指針

裸指針初始化–取地址符號&,取變量的地址賦值給指針變量

int year;
year = 2021;       // year 對應的變量塊中存放數2021
int *ptr_year;     // 聲明一個指針變量
ptr_year = &year;  // 將變量year的地址出來賦給指針變量,我們說的是ptr_year指向了year這個變量

1.2 操作裸指針–間接運算符*

操作裸指針–間接運算符*
間接運算符*作用于指針變量,取變量中的地址,然后對該地址對應的內存空間進行操作

int num = 1024;
int *ptr_num;
ptr_num = \#
*ptr_111;  //等價于 num = 111;

注意:指針聲明之星號 和 間接運算符之星號 的作用完全不同

1.3 裸指針使用 demo–指向一個簡單變量

int main(){double num = 1024.5;double *ptr_num = &num;cout << "ptr_num 的值: " << ptr_num << "\t" << &num << endl;cout << "ptr_num指向空間的值: " << *ptr_num << endl;return 0;
}

輸出:

ptr_num 的值: 0x7ffee273f630   0x7ffee273f630
ptr_num指向空間的值: 1024.5

demo2:字符指針在輸出時候的注意事項

int mian(){char ch = 'a';char *ptr_ch = &ch;// 默認以字符串的方式打印字符(char 型指針被默認為帶有間隔操作符號)       cout << ptr_ch << "\t" << *ptr_ch << endl;// 強制轉換成字符型指針(輸出地址,void * 任意的地址類型)cout << (void * )ptr_ch << "\t" << *ptr_ch << endl;return 0;
}

1.4 空指針–nullptr

空指針: 不指向任何對象指針。
作用: 初始化指針,避免出現野指針。
提示: 在使用一個指針前可以檢查它是否為空。


int *ptr1 = nullptr;        // c++ nullptr 字面值常量 =0, 可以被轉換成任何類型的指針
int *ptr2 = 0;# include <cstdlib>        // c 語法空指針
int *ptr3 = NULL

1.5 特殊指針–void *ptr

一種特殊的指針類型,可以存放各種類型變量的地址

注意1:void *指針不能用來訪問地址所指向的對象(即用* 取地址對應的內容)
void 使用技巧: 和別的指針比較、作為函數的輸入輸出、賦值給另一個void 指針

void 指針使用示例

int main(){// void 指針double objNum = 3.14;double *ptr_obj = &objNum;void *vptr_obj = &objNum;cout << (vptr_obj == ptr_obj) << endl;return 0;
}

2.指針和引用–引用定義&

引用:對象的一個別名,引用訪問變量時直接用引用名就可以了,不需要和指針一樣用*。

引用的定義

int int_val = 1024;
int& refValue = int_val; # 定義了變量int_val的引用refValue

引用的使用 :和所有的一般變量一樣使用即可

int num = 108;
int& rel_num = num;
rel_num = 118;               // 直接使用引用對變量賦值
cout << &num << '\t' << &rel_num << endl;
// 輸出 操作的是同一塊內存空間,在使用數組或者對象的引用時,才會凸顯其優勢
0x7ffee750f60c  0x7ffee750f60c

常量引用: 一般情況下常量的引用是錯的,但是如果一定要定義一個常量的引用給可以使用const

double ref = 100.0;//?
const double ref = 100.0;//??

引用和指針的關系

  1. 引用是對指針的簡單封裝,底層仍然是指針。
  2. 引用在獲取地址時,編譯器內部會進行* 操作。
  3. C++提倡使用引用,而少用指針
  4. 引用的優勢-效率更高。指針賦值時的取地址符號&會驗證地址的有限性(編譯器內部機制?)而引用不需要,所以引用使用起來效率更高。

注意事項:

  1. 引用只能綁定在對象上,不能與字面值或者某個表達式的計算結果綁定在一塊。
  2. 引用都必須初始化,所以引用使用之前不需要測試其有效性。

3.指針和數組

數組數據是一塊連續的內存地址,數組名就是這塊連續內存空間的首地址

3.1 數組指針的定義

int main(){double score[] = {11, 22, 33, 44, 55};double *ptr_score = score;    // 指向數組的指針,不需要取地址符號cout << sizeof(score) << '\t' << sizeof(ptr_score) << endl;cout << ptr_score[2] << endl;    // 數組指針可以像數組名一樣使用下標操作數組return 0;
}
// 輸出
40      8          # 數組名對應的數據類型為double[5]sizeof 輸出時是4033

3.2 數組指針遞增/遞減操作

指針的++,–被視為指針的移動操作,移動下一個/上一個基本單位

int main(){double score[5] = {98, 87, 65, 43, 76};double *ptr_score = score;for(int i = 0; i < 5; i++){cout << *ptr_score++ << endl;        // }return 0;
}

3.3 指針與數組使用的一些注意點

int num[50]; //num數組名,也可以理解成數組的首地址
// num的值和&num[0] 的值一致
// 數組第i+1個元素地址可以表示為:&num[i+1] num + i + 1
// 數組第i+1個元素可以表示為: num[i+1] 或者 *(num+i+1)
// 為指向數組的指針賦值
int *ptr_num = num;
int *ptr_num = &num[0];
//指針變量也可以指向數組元素
int *ptr_num = &num[4]
int *ptr_num = num + 4

本文來自互聯網用戶投稿,該文觀點僅代表作者本人,不代表本站立場。本站僅提供信息存儲空間服務,不擁有所有權,不承擔相關法律責任。
如若轉載,請注明出處:http://www.pswp.cn/news/444842.shtml
繁體地址,請注明出處:http://hk.pswp.cn/news/444842.shtml
英文地址,請注明出處:http://en.pswp.cn/news/444842.shtml

如若內容造成侵權/違法違規/事實不符,請聯系多彩編程網進行投訴反饋email:809451989@qq.com,一經查實,立即刪除!

相關文章

關于valgrind的安裝和內存泄露分析

程序的安裝 如果使用的是tar包安裝. valgrind # wget http://valgrind.org/downloads/valgrind-3.9.0.tar.bz2 # tar -jxvf valgrind-3.9.0.tar.bz2 # cd valgrind-3.9.0 # ./autogen.sh # ./configure # make; make install 使用命令: valgrind --tool=memcheck --leak-…

關于mysql的cpu占用高的問題

現在游戲開了泰服 ,發現泰服的cpu占用率總是比繁體或者大陸的高很多,每次都是占用了300%多 top - 15:34:06 up 222 days, 2:51, 2 users, load average: 0.75, 0.73, 0.66 Tasks: 215 total, 1 running, 214 sleeping, 0 stopped, 0 zombie Cpu(s): 52.4%us, 8.5%…

網絡原理知識點匯總

OSI七層模型 vs. TCP/IP 五層模型&#xff08;有時候也說四層&#xff09;及各層協議 七層&#xff1a;物理層&#xff1a;為數據端設備提供傳送數據的通路&#xff0c; IEEE802 數據鏈路層&#xff1a;提供介質訪問和鏈路管理&#xff0c; ARP&#xff0c;MTU 網絡層&#xf…

無限踩坑系列(8)--猿界神猿

計算機一句話冷知識1.GNU2. Unix與C語言3. Linux與git-hub4. c/c 編譯器5. python1.GNU GNU是一個自由的操作系統&#xff0c;其內容軟件完全以GPL方式發布。 GNU&#xff1a;GNU’s Not Unix!的遞歸縮寫 Unix 商業化之后&#xff0c; RMS發起了GNU計劃&#xff0c;在該計劃下…

C++實現md5加密或計算文件的唯一性識別

由于網絡上傳了很多關于C實現md5加密的類&#xff0c;至于那個是原創&#xff0c;我不敢妄加猜測&#xff0c;只是這里我聲明我是轉載的&#xff0c;并支持原創。 對于md5加密算法&#xff0c;我提供兩文件&#xff1a; #ifndef MD5_H #define MD5_H #include <string>…

Crontab的格式

第1列分鐘1&#xff5e;59 第2列小時1&#xff5e;23&#xff08;0表示子夜&#xff09; 第3列日1&#xff5e;31 第4列月1&#xff5e;12 第5列星期0&#xff5e;6&#xff08;0表示星期天&#xff09; 第6列要運行的命令 下面是crontab的格式&#xff1a; 分 時 日 月 星期 要…

leetcode516 最長回文子序列

給定一個字符串s&#xff0c;找到其中最長的回文子序列。可以假設s的最大長度為1000。 示例 1: 輸入: "bbbab" 輸出: 4 一個可能的最長回文子序列為 "bbbb"。 示例 2: 輸入: "cbbd" 輸出: 2 一個可能的最長回文子序列為 "bb"。 …

C++(10)--動態分配內存new,程序的內存分配

動態分配內存1. 動態分配內存1.1使用new分配內存1.2使用delete釋放內存1.3使用new創建動態分配的數組2. 程序的內存分配3.數組與指針案例實踐4.二維數組與指針《老九學堂C課程》《C primer》學習筆記。《老九學堂C課程》詳情請到B站搜索《老九零基礎學編程C入門》-------------…

社交app應用開發 客戶端+服務器源碼

原帖地址&#xff1a;http://www.devdiv.com/iOS_iPhone-想學習移動社交APP的童鞋有福了&#xff0c;圖文展示&#xff0c;附客戶端&#xff0c;服務端源碼。-thread-121444-1-1.html 想學習移動社交APP的童鞋有福了&#xff0c;圖文展示&#xff0c;附客戶端&#xff0c;服務…

leetcode83 刪除排序鏈表中的重復元素

給定一個排序鏈表&#xff0c;刪除所有重復的元素&#xff0c;使得每個元素只出現一次。 示例 1: 輸入: 1->1->2 輸出: 1->2 示例 2: 輸入: 1->1->2->3->3 輸出: 1->2->3 思路&#xff1a;判斷下一個是否相同即可。 /*** Definition for singl…

tcpdump的用法

第一種是關于類型的關鍵字&#xff0c;主要包括host&#xff0c;net&#xff0c;port, 例如 host 210.27.48.2&#xff0c;指明 210.27.48.2是一臺主機&#xff0c;net 202.0.0.0 指明 202.0.0.0是一個網絡地址&#xff0c;port 23 指明端口號是23。如果沒有指定類型&#xff0…

關于NFS服務器的原理總結和mount掛載

NFS 是Network File System的縮寫,即網絡文件系統。一種使用于分散式文件系統的協定,由Sun公司開發,于1984年向外公布。功能是通過網絡讓不同的機器、不同的操作系統能夠彼此分享個別的數據,讓應用程序在客戶端通過網絡訪問位于服務器磁盤中的數據,是在類Unix系統間實現磁…

leetcode203 移除鏈表元素

刪除鏈表中等于給定值 val 的所有節點。 示例: 輸入: 1->2->6->3->4->5->6, val 6 輸出: 1->2->3->4->5 思路&#xff1a;就刪唄&#xff0c;注意第一個數可能會被刪 /*** Definition for singly-linked list.* public class ListNode {* …

不需要安裝max或者xcode的object C開發環境

有時候很多人在沒有mac開發機的時候&#xff0c;都想著安裝一個虛擬mac機&#xff0c;或者用codeblock去配置成一個OC開發環境&#xff0c;我之前在學習OC的時候就這么辦過&#xff0c;虛擬機卡的要死&#xff0c;codeblock本來就不是專門用來做OC開發的&#xff0c;還要自己弄…

leetcode338 比特位計數

給定一個非負整數 num。對于 0 ≤ i ≤ num 范圍中的每個數字 i &#xff0c;計算其二進制數中的 1 的數目并將它們作為數組返回。 示例 1: 輸入: 2 輸出: [0,1,1] 示例 2: 輸入: 5 輸出: [0,1,1,2,1,2] 進階: 給出時間復雜度為O(n*sizeof(integer))的解答非常容易。但你可…

C++(11)--編程實踐1-經典養成類游戲簡單實踐

經典養成類游戲簡單實踐-小公主養成記《老九學堂C課程》學習筆記。《老九學堂C課程》詳情請到B站搜索《老九零基礎學編程C入門》-------------簡單的事情重復做&#xff0c;重復的事情用心做&#xff0c;用心的事情堅持做(老九君)---------------致敬&#xff1a;日本Gainax公司…

關于房屋的風水學整理

第一步&#xff1a;看缺角&#xff0c;根據戶型圖的整體形狀分析有無缺角戶型的形狀很多&#xff0c;有三角形的&#xff0c;手槍形的&#xff0c;鋸齒型的等等&#xff0c;總的來說缺角就不好&#xff0c;方方正正好&#xff0c;適合“天方地圓”。如下圖什么是缺角&#xff0…

房屋兇吉位判斷

房屋的吉兇位按八宅來判斷比較適合自身簡易的操作&#xff0c;但每個房屋&#xff0c;都是既有共性&#xff0c;也有個性的&#xff0c;具體的吉兇方位的判斷&#xff0c;可能要用到家中每個人的年命、運程&#xff0c;房屋周邊的山水形勢及地理環境要素。這些內容&#xff0c;…

leetcode226 反轉二叉樹

翻轉一棵二叉樹。 示例&#xff1a; 輸入&#xff1a; 4 / \ 2 7 / \ / \ 1 3 6 9 輸出&#xff1a; 4 / \ 7 2 / \ / \ 9 6 3 1 備注: 這個問題是受到 Max Howell 的 原問題 啟發的 &#xff1a; 谷歌&#xff1a;我們90&#xff05;的…