1.類的定義
1.1類定義格式
首先我們引入一個新的關鍵字-----class,class定義一個類。
定義方法
跟我們之前定義結構體非常的像
????????那我們來簡單的看一個類的定義
????????????????????????我們C語言實現的時候,結構體和函數是分離的。但是現在不需要,我可以直接寫? ? ? ? ? ? ? ? ? ? ?Push
????????????????????????
????????????????????????現在這些成員默認是什么?公有還是私有?。私有
????????????????????????如果我在這兒這樣寫呢?
????????????????????????
????????????????????????
????????????????????????那Push是公有還是私有?
????????????????????????
?????????????????????????私有
????????????????它跟結構體不一樣的地方在于
????????????????????????1
????????????????????????????????我們結構體是不是就是在結構里面定義一些變量啊?它除了可以定義變量? ? ? ? ? ? ? ? ? ? ? ? ? ? ?(我們一般叫成員變量或類的屬性(基本的特征值)),還可以定義函數(也叫類的? ? ? ? ? ? ? ? ? ? ? ? ?方法或成員函數)。
????????????????????????第二個和以前的區別
????????????????????????????????這個類名在這個地方就是類型
????????????????????????????????
????????????????????????????????那我們這個類型可以定義個對象,那我們用這個對象去訪問
????????????????????????????????
????????????????????????????????它可以訪問Pop,不能訪問Push。因為Push默認是私有的
????????????????????????????????那如果我想訪問這個Push呢?
????????????????????????????????我能不能同一個訪問限定符定義多個?
????????????????????????????????可以,但我們實際當中肯定不會這么玩,看起來太亂了。
????????????????????????????????
再看另一個類的定義
????????我怎么區分參數和成員變量呢?
? ? ? ??
? ? ? ? 這樣嗎?
????????
????????這樣寫就犧牲了我程序的可讀性了,我怎么知道y是什么,m是什么?
????????????????所以,C++慣例上面會給成員變量進行特殊標記:為了區分成員變量,?般習慣上成員? ? ? ? ? 變量會加?個特殊標識,如成員變量前?或者后?加_ 或者 m 開頭,注意C++中這個并不是? ? ? ? ? 強制的,只是?些慣例,具體看公司的要求。
????????在前面加一個_
?????????????
????????不過C++并沒有規范,所以就八仙過海各顯神通了。
????????
????????這個時候就能非常明顯的區分了
?????????
我能不能把這個成員變量放上面?或者把成員變量混在幾個函數中間可不可以?
都可以,C++沒有限制嗷。
但是一般情況下,稍微規范一點點,都是函數在上,成員變量在下。
C++中struct也可以定義類,C++兼容C中struct的?法,同時struct升級成了類,明顯的變化是struct中可以定義函數,?般情況下我們還是推薦?class定義類
????????C++中的struct也可以定義函數,C語言不可以。
????????
????????????????它跟class定義類幾乎沒有區別,唯一的區別在這里:class的默認訪問限定符是私有? ? ? ? ? ? ? ? 的,而struct的默認訪問限定符是公有的。
????????但是C++又兼容C語言之前的用法。
????????????????我這么定義,可不可以?-----可以。
????????????????
? ? ? ? ? ? ? ? ??所以C++有時候定義鏈表的節點是這么定義的。
??????????????????
? ? ? ? ? ? ? ? ??這個在C語言是編不過的,C語言必須得這樣。
? ? ? ? ? ? ? ? ??
? ? ? ? ? ? ? ? ??????????還有一種重大區別是什么呢?C語言咱們一般要typedef,因為咱們嫌寫struct太麻? ? ? ? ? ? ? ? ? ? 煩了。
? ? ? ? ? ? ? ? ? ? ? ? ??C++就不需要了
? ? ? ? ? ? ? ? ? ? ? ? ??
? ? ? ? ? ? ? ? ? ? ? ? ??但你之前的那一套,我都兼容。
? ? ? ? ? ? ? ? ? ? ? ? ??? ?
????????????????那我直接這樣定義可不可以呢?--------也可以。
????????????????
????????????????????????一般情況下,我們還是喜歡用class,只有一些少數的場景會用struct。什么場景? ? ? ? ? ? ? ? ? ? ? 呢?比如你所有成員都是公開的。
定義在類里面的成員函數默認為inline
????????也可以進行聲明和定義的分離。
????????
????????把定義寫類外面,但這樣我這些變量找不到啊(C++不是默認只會在局部和全局找嘛)。
????????
? ? ? ??所以定義得這樣寫
????????
????????????????你得指明,我這個函數不是一個全局函數,我是一個類的成員函數,只是聲明和定義分? ? ? ? ? ? 開了。
1.2訪問限定符
? ? ? ??C++類這個地方除了把數據和方法都放到一起,它還增加了一個叫訪問限定符的東西。
????????訪問限定符有3個????????????????????????????????????????????????????????????????????????????????????????????????
????????????????public(公有)
????????????????private(私有)
????????????????protected(保護)
? ? ? ? ? ? ? ? 它們在現階段沒有區別,在繼承以后才會有區別。
????????????????C++?種實現封裝的?式,?類將對象的屬性與?法結合在?塊,讓對象更? ? ? ? ? ? 加完善,通過訪問權限選擇性的將其接?(就是函數)提供給外部的??使?。
????????????????????????我呢,首先把這些數據和方法呢,我都放到了一起。放到一起了以后,我還想做一? ? ? ? ? ? ? ? ? ?些所謂的限制。
????????????????????????如果我想給你類外直接訪問的,我就定義成公有,否則,我就定義成protected和? ? ? ? ? ? ? ? ? ? ?private。
????????那訪問限定符是怎么限定的呢?
????????????????從該訪問限定符到下一個訪問限定符出現為止。
????????????????
????????????????如果后面沒有訪問限定符,那就到類結束
????????????????
????????????????
????????class定義的成員如果沒有訪問限定符,默認是ptivate,struct默認為public。
????????一般情況下,我們會把成員變量限制成protected或者private,需要給別?使?的成員函數會放為public
????????也就是說,我不希望你隨便修改我的數據。
1.3類域
????????我們之前說C++在有全局域,局部域,命名空間域,還有一個就是類域。
????????類定義了以后也形成了一個新的域。
????????為什么要形成一個新的域呢?
????????因為不行形成新的域也有問題啊。
????????你想想,你定義一個棧,你是不是有一個叫Push的函數啊?那我定義一個隊列,我也有一個叫Push的函數啊。
????????那我們兩個函數會不會沖突呢?不會沖突。因為我們在不同的域里面。
????????類域和命名空間域只影響名字隔離,不影響生命周期。
????????如果你在類外面,得指定類域
????????這個剛剛我們講過了(聲明和定義分離)。
????????類域影響的是編譯的查找規則,下?程序中Init如果不指定類域Stack,那么編譯器就把Init當成全局函數,那么編譯時,找不到array等成員的聲明/定義在哪?,就會報錯。指定類域Stack,就是知道Init是成員函數,當前域找不到的array等成員,就會到類域中去查找
????????
#include<iostream>
using namespace std;
class Stack
{public:// 成員函數void Init(int n = 4);private:// 成員變量int* array;size_t capacity;size_t top;
};
// 聲明和定義分離,需要指定類域
void Stack::Init(int n)
{array = (int*)malloc(sizeof(int) * n);if (nullptr == array){perror("malloc申請空間失敗");return;}capacity = n;top = 0;
}
int main()
{Stack st;st.Init();return 0;
}
????????類域沒有展開using之類的說法嗷,命名空間域才有
2.實例化
2.1實例化概念
????????實例化其實我們也很好理解。
????????問大家一個簡單的問題:這個東西是聲明還是定義?
????????
????????對于變量,聲明和定義的區別是什么呢?-------開不開空間。
????????????????定義開空間,聲明不開。
? ? ? ? 它是聲明。
????????????????我能不能這樣去訪問它?
????????????????
????????????????????????不能,因為它是聲明,它都沒空間你咋能這樣訪問呢?
????????????????它是聲明,它沒有開空間
????????????????什么時候才會開空間呢?
????????????????????????這兒是一個類型,用這個類型定義一個對象
????????????????????????
????????????????????????在官方的說法叫做實例化嗷(就是產生一個具體的實例嘛),就是用這個類型實例? ? ? ? ? ? ? ? ? 化出一個對象(翻譯的問題)。
????????類型和對象的關系是一對多。一個類可以實例化出n多個對象。
????????
????????怎么理解呢?
????????類就像我們的設計圖一樣,我們要建房子,我們有個設計圖。這個設計圖它是按比例縮小的,通過這個設計圖,我可以看到我的臥室有多大,我的客廳有多大,通過圖紙,我可以看到我房子的一切數據。
????????但是圖紙里面能不能住人?不能。
????????我用這個圖紙可以修出n多棟房子。
????????
????????這個房子是不是就可以住人了?
????????所以用類實例化出對象,就和我們用圖紙修房子是一樣的。
2.2對象大小
????????那這個對象的大小怎么算的?
????????????????我們簡單回顧一下,C語言之前講結構體里面是不是就存的成員對象,這些成員的大小? ? ? ? ? ? 要按照內存對齊的規則來計算。
????????????????那現在也是,不同的地方在于,我們要不要把成員函數的函數指針(函數本身肯定是不? ? ? ? ? 用存的,在庫里)存到對象里呢?
????????????????不需要,對象里面只要存成員變量即可。
????????????????????????為什么不需要?
????????????????????????????????我們用date實例化兩個對象
????????????????????????????????
????????????????????????????????d1和d2的年月日是不是一樣的?不一樣是不是?你d1得有你d1的年月日,d2? ? ? ? ? ? ? ? ? ? ? ? ? 得有d2的年月日。
????????????????????????????????那大家再想,d1和d2調的這兩個函數是相同的函數函數還是不同的函數?
????????????????????????????????????????我們說,不同的對象,他們的成員變量是不一樣的
????????????????????????????????????????但我們的函數是不是一樣的?是一樣的
????????????????????????????????????????????????那我們的函數是一樣的,我們在對象里面都存一份,這個時候會不? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? 會有浪費啊?
????????????????????????????????????????????????其實我們透過匯編這個層面上也能看到在這個地方是不是一樣的。
????????????????????????????????????????????????我們說函數被編譯完了是一段指令
????????????????????????????????????????????????
????????????????????????????????????????????????函數指針可以認為是第一句指令。
????????????????????????那這個函數指針存在哪兒呢?它會存到一個公共的地方。
????????????????????????這?需要再額外啰嗦?下,其實函數指針是不需要存儲的,函數指針是?個地址,? ? ? ? ? ? ? ? ? 調?函數被編譯成匯編指令[call 地址], 其實編譯器在編譯鏈接時,就要找到函數的地? ? ? ? ? ? ? ? ? ? 址,不是在運?時找,只有動態多態是在運?時找,就需要存儲函數地址,這個我們以? ? ? ? ? ? ? ? ? 后會講解。
????????????????上?我們分析了對象中只存儲成員變量,C++規定類實例化的對象也要符合內存對?的規則。? ? ? ??
-
內存對?規則
-
第?個成員在與結構體偏移量為0的地址處。
-
其他成員變量要對?到某個數字(對?數)的整數倍的地址處。
-
注意:對?數 = 編譯器默認的?個對?數 與 該成員??的較?值。
-
VS中默認的對?數為8
-
32位下默認是4
-
64位下默認是8
-
-
結構體總??為:最?對?數(所有變量類型最?者與默認對?參數取最?)的整數倍。
-
如果嵌套了結構體的情況,嵌套的結構體對?到??的最?對?數的整數倍處,結構體的整體??
-
就是所有最?對?數(含嵌套結構體的對?數)的整數倍。
-
????????????????????????那我們來算一下
????????????????????????
????????????????????????????????A
????????????????????????????????
????????????????????????????????B,C是0嗎?
????????????????????????????????如果是0,你這個b對象和c對象怎么定義出來的?
????????????????????????????????
????????????????????????????????我們說定義是不是就要開空間啊?如果我對b再取個地址,那我取個地址了以? ? ? ? ? ? ? ? ? ? ? ? ? ?后,地址到底是多少啊?
????????????????????????????????
? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? 難道是空指針?都沒有大小,那它地址是不是只能是空指針啊?
????????????????????????????????那我們看到實際過程當中,它再這兒的大小不是0
????????????????????????????????
????????????????????????????????我們剛才其實已經分析了,如果給0在這個地方其實挺難受的,你的地址到底? ? ? ? ? ? ? ? ? ? ? ? ? 是多少?
????????????????????????????????比如你定義了b1,b2,b3,它們的區別是什么?你怎么表示它存在過?因為定義? ? ? ? ? ? ? ? ? ? ? ? ? ? 就要開空間啊。
????????????????????????????????所以我們看到,如果類它沒有成員變量,我們都可以把它們簡稱為空類或沒? ? ? ? ? ? ? ? ? ? ? ? ? ? 有成員變量的類。它們的對象大小是1。
????????????????????????????????????????開1字節不是為了存儲什么數據,因為如果一個字節都不給,怎么表示對? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? 象存在過呢?
????????????????????????????????????????所以這里給一個字節呢,純粹是為了占位,表示對象存在。
????????????????????????????????????????這個時候你要取它的地址啊什么都好取。
????????????????????????????????那我們以后會定義這樣的類嗎?會定義,而且還不少。
????????????????????????????????????????以后我們會學習一個仿函數的類,這個類幾乎全是這種沒有成員變量的? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? 類。
????????????????為什么要內存對齊啊?
????????????????????????內存對齊不就浪費了嗎?方便查找(空間換時間,提升效率)。
????????????????????????????????怎么方便查找?
? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ????????如果不對齊會有什么問題?什么情況下會有問題啊?
????????????????????????????????????????首先,大家要理解內存對齊,要先知道一個東西。我們CPU來讀取內存? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ?數據的時候,他不是能夠從任意位置開始讀的。它在這個地方讀的時候,它? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ?一次有一個CPU的字長(不同的機器不同)。
? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ?那它一次性讀的時候,并不是說每次都能從任意位置開始讀。
????????????????????????????????????????????????如果我能從任意位置開始讀,讀任意大小,那左邊的設計毫無優? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ?勢,還浪費空間。
????????????????????????????????????????????????實際當中,在讀取數據的時候,它是從整數倍位置開始讀,一次讀? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? 4個字節(這個和具體的機器有關系,我們在這假設讀4個)。
????????????????????????????????????????????????為什么這樣設計呢?
????????????????????????????????????????????????讀取這些數據它是用一個叫數據總線的東西。
????????????????????????????????????????????????比如說4個字節(32個比特位)就有32根數據總線,因為在內存當? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? 中就是0101這樣的類似電信號位這樣的方式取存儲的嘛,那我在這個地? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? 方是不是就是看它到底是0還是1啊?
????????????????????????????????????????????????你就可以認為我就像一輛車,我一次就需要拉32個人,你如果從任? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ?意位置讀任意字節的話,我去這兒讀一個字節是不劃算的(意味著我一? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ?次只能拉4個人),所以我就規定我在這兒拉人,我一次就拉32個人。
????????????????????????????????????????????????我拉人的那個起點是規定的,就是從這個點開始拉,然后一次呢,? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? 不管你要拉多少人,我都給你拉32個人過來。
????????????????????????????????????????????????
????????????????????????????????????????????????也就意味著,它的讀取都是這個位置開始讀,都四個字節(假設? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ?嗷,實際不是這樣的,實際和具體的機器都有關系)。
????????????????????????????????????????????????
????????????????????????????????????????????????那也就意味著從這個位置開始讀4個字節,不管是左邊還是右邊,? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? 都是這樣讀的。
????????????????????????????????????????????????那大家看在這個地方,我們在這個地方訪問這個數據的時候。
????????????????????????????????????????????????????????如果是左邊這樣的設計,我讀了4個字節,我只要第一個字節
????????????????????????????????????????????????????????
????????????????????????????????????????????????????????如果是右邊這樣的設計,我要讀這個_i,我能不能從第一個字? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ?節這個位置開始讀4個字節?
????????????????????????????????????????????????????????
????????????????????????????????????????????????????????不能,因為它必須從整數倍的位置開始讀。
????????????????????????????????????????????????????????那就只能從這個位置開始讀,讀4個字節,留下后3個字節。
????????????????????????????????????????????????????????
????????????????????????????????????????????????????????再從這個位置開始讀,讀4個字節,留下第一個字節。
????????????????????????????????????????????????????????
????????????????????????????????????????????????????????再用第一次讀到的3個字節和那一個字節進行拼接,拼出的這? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? 個字節才是我們的_i。
????????????????????????????????????????????????????????我們得讀兩次才能讀取到我們的_i,而且很麻煩很復雜。
????????????????????????????????????????????????????????所以,基于這樣的原因,內存對齊是不是就有它的優勢啦?
3.this指針
????????Date類中有 Init 與 Print 兩個成員函數,函數體中沒有關于不同對象的區分,那當d1調?Init和Print函數時,該函數是如何知道應該訪問的是d1對象還是d2對象呢?那么這?就要看到C++給了?個隱含的this指針解決這?的問題。
????????那這個隱含的this指針是什么情況呢?
????????其實你看到的這些函數,它的第一個參數不是year,Print也不是沒有參數
????????
????????它們都有一個隱含的參數,這個隱含的參數,規定叫this
????????
????????this也是一個c++新增的關鍵字。
????????那這個隱含的this指針是誰呢?在調用的時候,這個位置它會悄悄的把d1的地址傳過去。????????????????
????????那這個時候我就知道誰是d1,誰是d2了呀,因為this就是指向你這個地方的調用對象的。
????????
????????那這個時候Init和Print的是不是就是d1的年月日啊?
????????怎么做到d1的年月日的呢?
????????還有一步。這里面訪問年月日其實是通過this訪問的。
????????
????????這個時候就能完美的做到區分了。
??????this 指針是一個隱含于每一個非靜態成員函數中的特殊指針
? ? ? C++規定不能在實參和形參的位置顯式的寫this指針(編譯時編譯器會處理),但是可以在函數體內顯式使用this指針。
? ? ? ? ?也就意味著,如果你想在這兒顯式的寫,不行
????????????????實參
????????????????
????????????????形參
????????????????????????
????????但是,我在函數體內可以使用這個this指針
????????
????????為什么會這么規定?
????????實參形參讓你自己寫會變混亂,不如讓編譯器自己去搞。
????????在函數體內有些地方必須要用this,我們后面會看到,你不寫,他會自動給你加上,你寫了,它也可以兼容。
????????this指針是不能修改的
????????????????因為this指針是const修飾的
????????????????
????????????????但它指向的內容是可以修改的
????????????????
????????this指針是存在哪個區域的?
? ? ? ?????????是不是存在對象里面的?????????
????????????????一定不是存在對象里面。
????????????????我們剛剛講了,算對象大小的時候你有沒有算this指針?----沒有吧。那this指針憑什么? ? ? ? ? ? ?在對象里面?
????????????????那在哪個區域比較合理呢?
????????????????它是一個形參,那形參這些參數是存在哪兒的呢?
????????????????????????棧幀里面的對不對?
????????????????????????在VS下,由于this指針頻繁使用,它存在了寄存器下。所以有些地方說它放到寄存器也是對的啊。所以這個地方要具體問題具體分析。
????????????????????????
????????????????????????傳統意義上我們還是認為它是形參,存在棧幀里面。
? ? ? ? ? this指針的生命周期是和對象本身緊密相關的
? ? ? ? ? 我們來看倆題
????????????????????????
????????????????那到底是運行崩潰還是正常運行呢?
????????????????這個題是正常運行
????????????????
????????????????為什么是正常運行,沒有產生崩潰呢?
????????????????這個空指針這樣走難道沒有解引用嗎?
????????????????
????????????????這個時候就不得不拋出一個問題了
????????????????編譯器被編譯了以后,底層都會干嘛?是不是都會轉換成匯編指令啊?
????????????????按我們剛剛講的,這個地方轉換成的匯編是什么?
????????????????
????????????????是不是call一個地址啊?
????????????????
????????????????那這個地址在哪兒?在不在對象里面?
????????????????????????不在,因為我們前面講了,成員函數的指針不存到對象里面。
????????????????????????成員函數編譯,編譯好了是一段指令,它在符號表里面,編譯的時候,通過函數名? ? ? ? ? ? ? ? ? ?就確定了這個地方的地址,和這個對象沒關系
????????????????????????
????????????????????????那為什么需要對象去調用呢?
????????????????????????????????一個是對象類域嘛,它是屬于它的成員函數。
????????????????????????????????那你在這兒p調用,我是A類型,編譯的時候它就知道去A類里面去找。
????????????????????????????????
????????????????????????????????其次,要傳遞this指針。
????????????????????????????????調用函數是不是要傳參數啊?(傳參數,以前是lea,因為是對象,lea是取地址? ? ? ? ? ? ? ? ? ? ? ? ? ? ?嘛)。
????????????????????????????????這個地方需不需要取地址?不需要取地址了,因為p就是對象的地址啊(這兒? ? ? ? ? ? ? ? ? ? ? ? ? 是對象的指針啊)。
????????????????????????????????這個地方應該是這個,ecx相當于存的是this指針
????????????????????????????????
????????????????????????????????然后再call這個地址
????????????????????????????????
????????????????????????過來就調用這個函數,這個函數里面的this是空指針
????????????????????????
????????????????????????空指針會報錯嗎?
????????????????????????我有一個空指針,我沒有去解引用訪問,會報錯嗎?不會。
????????????????????????不要看到箭頭就以為要解引用。
????????????????????????這個時候會不會解引用啊?(解引用是指獲取指針所指向地址中存儲的值的操作)? ? ? ? ? ? ? ? ? ? ?會。
????????????????????????
????????????????????????因為成員變量是存在對象里的。這個時候才會崩潰。
????????????????????????
????????????????這個會崩潰
????????????????
4.C++和C語?實現Stack對?
面向對象有三大特性:封裝、繼承、多態
我們來對比一下C和C++
?????????這里是我們C語言實現的棧
????????????????
????????????????
????????????????C語言
????????????????數據是放到結構體
????????????????函數是函數
????????????????????????函數要訪問數據,得把數據的地址傳過來
????????????????這是我們當前學的知識(僅限于當前學的知識哦)定義的棧
????????????????????????C++:數據和方法都放到了類里面
????????????????????????形態上是不是發生了一些變化啊?但是本質變沒變?
????????????????????????沒有變化
????????????????????????
在我們這個C++??階段實現的Stack看起來變了很多,但是實質上變化不?。等著我們后?看STL中的?適配器實現的Stack,?家再感受C++的魅?
????????C++類的設計最大的變化是這個面向對象三大特性之一-----封裝。
????????面向對象在這里提出了三大特性
????????????????封裝
????????????????????????這里呢,真正的體現是這個封裝。
????????????????????????????????C語言它是比較自由的。它的數據是隨便訪問的,方法也是這樣的。
????????????????????????????????????????舉例:我們在這兒訪問棧頂數據,我可以調STTop()。
? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ?但它也能這樣
??????????????????????????????????????????????????????????????????
? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ?????????所以就導致了用C語言實現這些東西的時候很不規范。
????????????????????????????????C++就不能采取這樣的方式去訪問數據了
? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? 為什么?
? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? 你訪問不了
? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ?因為我們C++建議把成員變量都搞成私有的,這就在語法上限制了你在? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ?外面不能隨便訪問我的成員變量。
? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ?也就是說,你想訪問我的成員變量,你得通過成員函數,哪怕像? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ?TopSize()這樣的(就一行代碼)你也得通過成員函數來訪問。
? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ?那我的成員函數只要實現的沒錯,你就不會亂搞。它是更規范的。
? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ?C語言數據和方法是分離的,也沒有任何訪問限定符。C++把數據和方法放? ? ? ? ? ? ? ? ? ? ? ? ? ? ?到一起。想給你直接訪問的,放成共有。不想給你訪問的,放成私有。
? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ??這是一種封裝規范管理。C++中數據和函數都放到了類??,通過訪問限? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? 定符進?了限制,不能再隨意通過對象直接修改數據,這是C++封裝的?種體? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? 現,這個是最重要的變化。這?的封裝的本質是?種更嚴格規范的管理,避免出? ? ? ? ? ? ? ? ? ? ? ? ? ? ? 現亂訪問修改的問題。當然封裝不僅僅是這樣的,我們后?還需要不斷的去學? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? 習。
????????????????????????繼承
????????????????????????多態
? ? ? ? ? ? ? ? ? ? ? ? ? ?我們后面會講。